﻿///<jscompress sourcefile="VFGMap.js" />
VFG.Viewer=function(option){
	if(!option){
		console.log('参数必填!!!');
		return;
	}
	this.url=option.url||'';
	this.ws=option.ws||'';
	this.domId=option.domId||''
	this.sceneId=option.sceneId||''
	this.homeId=option.homeId||null;
	this.geocoder=option.geocoder||false;
	this.complete=option.complete||null;
	this.progress=option.progress||null;
	
	this.scene;
	this.init();
}

VFG.Viewer.prototype.init=function(){
	var _this=this;
	if(_this.homeId){
		_this.callBackProgress('开始请求加载资源！！！');
		_this.ajaxFunc(_this.url+"/api/scene/getDefualtSrc",{sceneId:_this.sceneId,pageId:_this.homeId}, "json", function(res){
	    	 if (undefined!=res && 200==res.code) {
	    		 _this.callBackProgress('资源加载成功，开始渲染！！！');
	    		 _this.initGlobe(res.data)
	    	 }else{
	    		 if(undefined==res){
	    			 _this.callBackProgress('资源服务异常！！！');
	    		 }else{
	    			 _this.callBackProgress(res.message);
	    		 }
	    	 }
		})
	}else{
	    _this.ajaxFunc(_this.url+"/api/scene/getById",{sceneId:_this.sceneId}, "json", function(res){
	        if (undefined!=res && 200==res.code) {
	    		 _this.callBackProgress('资源加载成功，开始渲染！！！');
	    		 _this.initDefaultGlobe(res.data)
	        }else{
	    		 if(undefined==res){
	    			 _this.callBackProgress('资源服务异常！！！');
	    		 }else{
	    			 _this.callBackProgress(res.message);
	    		 }
	            if(_this.complete){
	            	_this.complete({
	            		code:500,
	            		message:'配置场景不存在！',
	            	});
	            }
	        }    	
	    	
	    });
	}
	
}

/**
 * 初始化球体
 */
VFG.Viewer.prototype.initGlobe=function(data){
	var _this=this;
	var Point=data.Point;
	var Line=data.Line;
	var Polygon=data.Polygon;
	var Model=data.Model;
	var Map=data.Map||null;
	this.menuTree=data.menuTree;
	this.menuMap=data.menuMap;
	this.POINT_STYLE=data.POINT_STYLE;
	this.LINE_STYLE=data.LINE_STYLE;
	this.POLYGON_STYLE=data.POLYGON_STYLE;
	this.SCENE_MENU_MAP_ID=data.SCENE_MENU_MAP_ID;
	this.SCENE_MENU_MAP_CODE=data.SCENE_MENU_MAP_CODE;
	_this.HOME=data.HOME;
	_this.ellipsoid = Cesium.Ellipsoid.WGS84;
	_this.globe = new VFG.Globe({
		domId: _this.domId,
		geocoder: _this.geocoder,
		imageryProvider:new Cesium.TileMapServiceImageryProvider({
			url:_this.url+"/assets/plugins/Cesium/Assets/Textures/NaturalEarthII",
		})
	});
	_this.viewer=_this.globe.viewer;
	_this.scene=_this.globe.viewer.scene;
	_this.tip=new VFG.Tip(_this.viewer);
	_this.handler = new Cesium.ScreenSpaceEventHandler(_this.viewer.scene.canvas);
	_this.callBackProgress('加载底图！！！');
	
	//资源加载
	_this.batchAddProviderForMap(Map);
	_this.batchAddPointForMap(Point);
	_this.batchAddPolylineForMap(Line);
	_this.batchAddModelForMap(Model);
	_this.batchAddPolygonForMap(Polygon);
	
	if(_this.HOME.cameraX && _this.HOME.cameraX && _this.HOME.cameraZ && _this.HOME.heading && _this.HOME.pitch && _this.HOME.roll){
		var lnla=VFG.Util.getC3ToLnLa(_this.viewer, new Cesium.Cartesian3(_this.HOME.cameraX*1,_this.HOME.cameraY*1,_this.HOME.cameraZ*1));
        var ln=lnla.x;
        var la=lnla.y;
        var alt=lnla.z;
		var x=0;y=0;z=0;
        var interVal = window.setInterval(function() {
        	if(x<ln){
        		_this.viewer.scene.camera.setView({
                    destination: new Cesium.Cartesian3.fromDegrees(x, y, z || 20000000)
                });
        		x+=1;
        	}else{
                clearInterval(interVal);
                _this.flyToDefault(_this.HOME);
        	}
        },10);
	}
	_this.callBackProgress('结束！！！');
    if(_this.complete){
    	_this.complete({
    		code:200,
    		message:'场景加载完成！',
    		globe:_this
    	});
    }
}

VFG.Viewer.prototype.initDefaultGlobe=function(data){
	var _this=this;
	var scene=data.scene;
	var maps=data.maps;
	this.POINT_STYLE=data.POINT_STYLE;
	this.LINE_STYLE=data.LINE_STYLE;
	this.POLYGON_STYLE=data.POLYGON_STYLE;
	this.SCENE_MENU_MAP_ID=data.SCENE_MENU_MAP_ID;
	this.SCENE_MENU_MAP_CODE=data.SCENE_MENU_MAP_CODE;
	_this.ellipsoid = Cesium.Ellipsoid.WGS84;
	_this.globe = new VFG.Globe({
		domId: _this.domId,
		geocoder: _this.geocoder,
		imageryProvider:_this.getDefaultProviderForList(maps)
	});
	_this.viewer=_this.globe.viewer;
	_this.scene=_this.globe.viewer.scene;
	_this.tip=new VFG.Tip(_this.viewer);
	_this.handler = new Cesium.ScreenSpaceEventHandler(_this.viewer.scene.canvas);
	//加载地图
	_this.callBackProgress('加载底图！！！');
	if(maps!=null && maps.length>0){
    	VFG.Provider.addImageryProvidersFromServ(_this.viewer,maps)
	}
	if(scene.cameraX && scene.cameraX && scene.cameraZ && scene.heading && scene.pitch && scene.roll){
		var lnla=VFG.Util.getC3ToLnLa(_this.viewer, new Cesium.Cartesian3(scene.cameraX*1,scene.cameraY*1,scene.cameraZ*1));
        var ln=lnla.x;
        var la=lnla.y;
        var alt=lnla.z;
		var x=0;y=0;z=0;
        var interVal = window.setInterval(function() {
        	if(x<ln){
        		_this.viewer.scene.camera.setView({
                    destination: new Cesium.Cartesian3.fromDegrees(x, y, z || 20000000)
                });
        		x+=1;
        	}else{
                clearInterval(interVal);
                _this.flyToDefault(scene);
        	}
        },10);
	}
	_this.callBackProgress('结束！！！');
    if(_this.complete){
    	_this.complete({
    		code:200,
    		message:'场景加载完成！',
    		globe:_this
    	});
    }
}

/**
 * 获取默认底图
 */
VFG.Viewer.prototype.getDefaultProviderForMap=function(map){
	var providerIMG=null;
	if(map!=null){
		for(var key in map){
		  var list=map[key];
		  if(list){
			  for(var i=0;i<list.length;i++){
					var map=list[i];
					if('map'==map.dataType){
						var provider= VFG.Provider.getImageryProviderFromServ(map);
						VFG.Provider.Map.set(map.id,provider);
						providerIMG=provider;
						break;
					}
			  }
		  }
		  if(providerIMG){
			  break;
		  }
	   }
	}
	return providerIMG;
}

VFG.Viewer.prototype.getDefaultProviderForList=function(list){
	if(list!=null){
		for(var i=0;i<list.length;i++){
			var map=list[i];
			if('map'==map.dataType){
				var provider= VFG.Provider.getImageryProviderFromServ(map);
				VFG.Provider.Map.set(map.id,provider);
				return provider;
			}
		}
	}else{
		return new Cesium.TileMapServiceImageryProvider({
			url:this.url+"/assets/plugins/Cesium/Assets/Textures/NaturalEarthII",
		});
	}
}

VFG.Viewer.prototype.callBackProgress=function(msg){
	if(this.progress){
		this.progress(msg);
	}
}

/**
 * 飞至默认视角
 */
VFG.Viewer.prototype.flyToDefault=function(data){
	var _this=this;
	if(data.cameraX && data.cameraX && data.cameraZ && data.heading && data.pitch && data.roll){
        _this.viewer.camera.flyTo({
            destination: new Cesium.Cartesian3(data.cameraX*1,data.cameraY*1,data.cameraZ*1),
            complete: function () {
            	_this.viewer.scene.camera.flyTo({
        	        duration:1,
        			destination: new Cesium.Cartesian3(data.cameraX*1,data.cameraY*1,data.cameraZ*1),
        			orientation:{
                		heading:data.heading*1,
                		pitch: data.pitch*1,
                		roll: data.roll*1,
                	}
        		});
            }
        });
	}
}

VFG.Viewer.prototype.destroy=function(){
	var _this = this;
	try{
		_this.closeWebSocket();
		_this.handler.destroy();
		if(_this.handler3D){
			_this.handler3D.destroy();
		}
		_this.globe.destroy();
	}catch (e) {
	}
}

;
///<jscompress sourcefile="VFGMapEvent.js" />
/**
 * 鼠标左键单击拾取实体
 * complete(c2,data)：回调函数
 */
VFG.Viewer.prototype.LEFT_CLICK_PRIMITIVE=function(callback){
	var _this=this;
	_this.handler.setInputAction(function(movement) {
		var obj = _this.viewer.scene.pick(movement.position);
		if (Cesium.defined(obj) && obj.primitive && obj.id){
			 if (obj.primitive instanceof Cesium.ClassificationPrimitive){
		    	if(callback){
		    		callback(movement.position,obj.id.id);
		    	}
			 }
			 else if (obj.primitive instanceof Cesium.PointPrimitive){
		    	if(callback){
		    		callback(movement.position,obj.primitive.id,'Point');
		    	}
			 }
			 else if (obj.primitive instanceof Cesium.Billboard){
		    	if(callback){
		    		callback(movement.position,obj.primitive.id,'Point');
		    	}
			 }
			 else if(obj.id.polygon){
		    	if(callback){
		    		callback(movement.position,obj.id.id,'Polygon');
		    	}
			 }else if(obj.id.polyline){
		    	if(callback){
		    		callback(movement.position,obj.id.id,'Line');
		    	}
			 }
		}
		
	}, Cesium.ScreenSpaceEventType.LEFT_CLICK);
}

/**
 * 鼠标双击事件
 */
VFG.Viewer.prototype.LEFT_DOUBLE_CLICK_PRIMITIVE=function(callback){
	var _this=this;
	this.handler.setInputAction(function(movement) {
		var obj = _this.viewer.scene.pick(movement.position);
		if (Cesium.defined(obj)){
			if(obj.id && (obj.id.point ||obj.id.billboard || obj.id.label) ){
		    	if(callback){
		    		callback(movement.position,obj.id.id);
		    	}
			}
			else if(obj.id &&obj.id.polyline){
			}
			else if(obj.id && obj.id.polygon){

			}
			else if(obj.primitive && obj.primitive.gltf){
			}
			else if (Cesium.defined(obj) && obj.primitive && obj.id){
				if (obj.primitive instanceof Cesium.ClassificationPrimitive){
				}
				else if (obj.primitive instanceof Cesium.PointPrimitive){
					callback(movement.position,obj.id);
					 _this.changePointPrimitiveStyle(obj.primitive.id,'SELECTD');
				}
				else if (obj.primitive instanceof Cesium.Billboard){
					callback(movement.position,obj.id);
					_this.changePointPrimitiveStyle(obj.primitive.id,'SELECTD');
				}
			}
		}
	}, Cesium.ScreenSpaceEventType.LEFT_DOUBLE_CLICK);
}

/**
 * 鼠标右键
 */
VFG.Viewer.prototype.RIGHT_CLICK_PRIMITIVE=function(callback){
	var _this=this;
	this.handler.setInputAction(function(movement) {
		var obj = _this.viewer.scene.pick(movement.position);
		if (Cesium.defined(obj)){
			if(obj.id && (obj.id.point ||obj.id.billboard || obj.id.label) ){
		    	if(callback){
		    		callback(movement.position,obj.id.id);
		    	}
			}
			else if(obj.id &&obj.id.polyline){
			}
			else if(obj.id && obj.id.polygon){

			}
			else if(obj.primitive && obj.primitive.gltf){
			}
			else if (Cesium.defined(obj) && obj.primitive && obj.id){
				if (obj.primitive instanceof Cesium.ClassificationPrimitive){
				}
				else if (obj.primitive instanceof Cesium.PointPrimitive){
					callback(movement.position,obj.id);
					 _this.changePointPrimitiveStyle(obj.primitive.id,'SELECTD');
				}
				else if (obj.primitive instanceof Cesium.Billboard){
					callback(movement.position,obj.id);
					_this.changePointPrimitiveStyle(obj.primitive.id,'SELECTD');
				}
			}
		}
	}, Cesium.ScreenSpaceEventType.RIGHT_CLICK);
}


/**
 * 鼠标滑过效果
 */
VFG.Viewer.prototype.MOUSE_MOVE_PRIMITIVE=function(callback){
	var _this=this;
	var currentEntity = null;
	var lastEntity = null;
	this.handler.setInputAction(function(movement) {
		var obj = _this.viewer.scene.pick(movement.endPosition);
		
		if (lastEntity!=null && lastEntity.primitive && lastEntity.id) {
			 if (lastEntity.primitive instanceof Cesium.ClassificationPrimitive){
				 var feature=VFG.Model.Feature.getFeatureById(lastEntity.id);
				 if(feature){
					 feature.leave();
				 }
			 }
			 else if(lastEntity.primitive instanceof Cesium.PointPrimitive){
				 _this.changePointPrimitiveStyle(lastEntity.primitive.id,'DEFAULT');
				 _this.tip.setVisible(false);
			 }
			 else if(lastEntity.primitive instanceof Cesium.Billboard){
				 _this.changePointPrimitiveStyle(lastEntity.primitive.id,'DEFAULT');
				 _this.tip.setVisible(false);
			 }
			 else if(lastEntity.id.polygon){
				 _this.changePolygonEntityStyle(lastEntity.id.id,'DEFAULT');
				 _this.tip.setVisible(false);
			 }
			 else if(lastEntity.id.polyline){
				 _this.changePolylineEntityStyle(lastEntity.id.id,'DEFAULT');
				 _this.tip.setVisible(false);
			 }
			 lastEntity=null;
		}
		
		
		if (Cesium.defined(obj) && obj.primitive && obj.id){
			 if (obj.primitive instanceof Cesium.ClassificationPrimitive){
				 currentEntity = obj;
				 lastEntity = currentEntity;
				 var feature=VFG.Model.Feature.getFeatureById(obj.id);
				 if(feature){
					feature.enter();
				 }
			 }
			 else if (obj.primitive instanceof Cesium.PointPrimitive){
				 currentEntity = obj;
				 lastEntity = currentEntity;
				 _this.changePointPrimitiveStyle(obj.primitive.id,'HOVER');
				 if(VFG.Point.Primitives.has(obj.id)){
					 _this.tip.showAt(movement.endPosition, `<div class="con" style="color: white;">`+VFG.Point.Primitives.get(obj.id).name+`</div>`);
				 }
			 }
			 else if (obj.primitive instanceof Cesium.Billboard){
				 currentEntity = obj;
				 lastEntity = currentEntity;
				 _this.changePointPrimitiveStyle(obj.primitive.id,'HOVER');
				 if(VFG.Point.Primitives.has(obj.id)){
					 _this.tip.showAt(movement.endPosition, `<div class="con" style="color: white;">`+VFG.Point.Primitives.get(obj.id).name+`</div>`);
				 }
			 }
			 else if((obj.id.point ||obj.id.billboard || obj.id.label)){
			 }else if(obj.id.polygon){
				currentEntity = obj;
				lastEntity = currentEntity;
				 if(obj.id.name){
					 _this.tip.showAt(movement.endPosition, `<div class="con" style="color: white;">`+obj.id.name+`</div>`);
				 }
				_this.changePolygonEntityStyle(obj.id.id,'HOVER');
			 }else if(obj.id.polyline){
				currentEntity = obj;
				lastEntity = currentEntity;
				 if(obj.id.name){
					 _this.tip.showAt(movement.endPosition, `<div class="con" style="color: white;">`+obj.id.name+`</div>`);
				 }
				_this.changePolylineEntityStyle(obj.id.id,'HOVER');
			 }
		}
	}, Cesium.ScreenSpaceEventType.MOUSE_MOVE);
}

;
///<jscompress sourcefile="VFGMapFlight.js" />
/**
 * 漫游对象缓存
 */
VFG.Viewer.prototype.Flight=new Map();

/**
 * option{
 *   id:路线id
 *   auto:（true/false）自动执行
 *   before:获取数据准备执行
 *   complete(对象):完成
 *   error（错误信息）：异常
 *   process(坐标、点信息)：实时
 * }
 */
VFG.Viewer.prototype.startForFly = function (option) {
	var _this=this;
	if(_this.Flight.has(option.id)){
	    _this.ajaxFunc(_this.ctx+"/biz/flight/getFlightRender",{flightId:option.id}, "json", function(res){
	        if (undefined!=res && 200==res.code) {
	        	option.flight=res.data
	        	var flightPrimitive=VFG.VFGFlightPrimitive(_this.viewer,option);
	        	 if(option.before) option.before(flightPrimitive);
	        	_this.Flight.set(option.id,flightPrimitive);
	       }else{
	    	   if(option.error) option.callback(res);
	       }
	    });
	}
}

/**
 * 暂停
 */
VFG.Viewer.prototype.pauseForFly = function (option) {
	var _this=this;
	if(_this.Flight.has(option.id)){
		var flight=_this.Flight.get(option.id);
		flight.pause();
		if(option.callback) option.callback(flight);
	}
}

/**
 * 停止并销毁对象
 */
VFG.Viewer.prototype.stopForFly = function (option) {
	var _this=this;
	if(_this.Flight.has(option.id)){
		var flight=_this.Flight.get(option.id);
		flight.stop();
		if(option.callback) option.callback(flight);
		_this.Flight.delete(option.id)
		//切换默认漫游菜单视角
	}
}

;
///<jscompress sourcefile="VFGMapLayer.js" />
VFG.Viewer.prototype.showOrHideLayer=function(option){
	var _this=this;
	var layerId=option.layerId;
	var type=option.type;
	var state=option.state;
	if('Point'==type){
		_this.showOrHidePoint(layerId,state)
	}
	else if('Line'==type){
		_this.showOrHidePolyline(layerId,state)
	}
	else if('Polygon'==type){
		_this.showOrHidePolygon(layerId,state)
	}
	else if('Model'==type){
		_this.showOrHideModel(layerId,state)
	}
	else if('Map'==type){
		_this.showOrHideProvider(layerId,state)
	}
}

VFG.Viewer.prototype.showOrHideLayerByCode=function(option){
	var _this=this;
	var menu=_this.getSceneMenuByCode(option.code);
	if(menu){
		option.layerId=menu.layerId;
		option.type=menu.type;
		_this.showOrHideLayer(option)
	}
}

/**
 * 根据页面code获取menu
 */
VFG.Viewer.prototype.getSceneMenuByCode=function(code){
	var _this=this;
	if(_this.SCENE_MENU_MAP_CODE.has(code)){
		return _this.SCENE_MENU_MAP_CODE[code];
	}
}

VFG.Viewer.prototype.changePrimitiveStyle=function(id,event,type){
	var _this=this;
	if('Point'==type){
		_this.changePointPrimitiveStyle(id,event)
	}
	else if('Line'==type){
		_this.changePolylineEntityStyle(id,event)
	}
	else if('Polygon'==type){
		_this.changePolygonEntityStyle(id,event)
	}
	else if('Model'==type){
	}
	else if('Map'==type){
	}
}
;
///<jscompress sourcefile="VFGMapListener.js" />
/**
 * 监听集合
 */
VFG.Viewer.prototype.ListenerMap=new Map();
/**
 * 监听屏幕坐标
 * 	bizPoint
 *  callBack:fun(c2)回调函数
 */
VFG.Viewer.prototype.addListenerScreenPosition  = function(bizPoint,callBack) {
	if(!bizPoint)return;
	if(!this.ListenerMap.has(bizPoint.id)){
		var option = {
			position:{
		  		x:bizPoint.x*1,
		  		y:bizPoint.y*1,
		  		z:bizPoint.z*1
			},
			id:bizPoint.id,
			callBack:callBack
		}
		var listener=new VFG.Listener(this.viewer,option);
		this.ListenerMap.has(bizPoint.id,listener);
	}
}

/**
 * 移出
 */
VFG.Viewer.prototype.removeListenerScreenPosition= function(id) {
	if(this.ListenerMap.has(id)){
		var listener=this.ListenerMap.get(id).destroy();
		this.ListenerMap.delete(id)
	}
}

VFG.Viewer.prototype.addListenerCamera=function(callback){
	var _this=this;
	_this.removeListenerCamera();
	_this.handler3D = new Cesium.ScreenSpaceEventHandler(_this.viewer.scene.canvas);
	var viewer=this.viewer;
	_this.handler3D.setInputAction(function(movement) {
	    var pick= new Cesium.Cartesian2(movement.endPosition.x,movement.endPosition.y);
	    if(pick){
	        var cartesian = _this.viewer.scene.globe.pick(_this.viewer.camera.getPickRay(pick), viewer.scene);
	        if(cartesian){
	            // 世界坐标转地理坐标（弧度）
	            var cartographic = _this.viewer.scene.globe.ellipsoid.cartesianToCartographic(cartesian);
	            if(cartographic){
	                // 海拔
	                var height = _this.viewer.scene.globe.getHeight(cartographic);
	                // 视角海拔高度
	                var he = Math.sqrt(_this.viewer.scene.camera.positionWC.x * _this.viewer.scene.camera.positionWC.x + _this.viewer.scene.camera.positionWC.y * _this.viewer.scene.camera.positionWC.y + viewer.scene.camera.positionWC.z * _this.viewer.scene.camera.positionWC.z);
	                var he2 = Math.sqrt(cartesian.x * cartesian.x + cartesian.y * cartesian.y + cartesian.z * cartesian.z);
	                // 地理坐标（弧度）转经纬度坐标
	                var point=[ cartographic.longitude / Math.PI * 180, cartographic.latitude / Math.PI * 180];
	                if(!height){
	                    height = 0;
	                }
	                if(!he){
	                    he = 0;
	                }
	                if(!he2){
	                    he2 = 0;
	                }
	                if(!point){
	                    point = [0,0];
	                }
	                var level=0;
                    var tilesToRender = _this.viewer.scene.globe._surface._tilesToRender;
                    if(tilesToRender.length>0){
                    	level= tilesToRender[0].level;
                    }else{
                    	level=0;
                    }
                    
                    var heading = Cesium.Math.toDegrees(_this.viewer.camera.heading).toFixed(2)*1;;
                    var pitch = Cesium.Math.toDegrees(_this.viewer.camera.pitch).toFixed(2)*1;;
                    var roll = Cesium.Math.toDegrees(_this.viewer.camera.roll).toFixed(2)*1;;
                    
                    if(callback){
                    	callback({
                    		position:{
                    			x:point[0].toFixed(6),
                    			y:point[1].toFixed(6),
                    			z:height.toFixed(2)
                    		},
                    		zoom:level,
                    		camera:{
                    			heading:heading,
                    			pitch:pitch,
                    			roll:roll,
                    		}
                    	});
                    }
	            }
	        }
	    }
	    
	}, Cesium.ScreenSpaceEventType.MOUSE_MOVE);
}
VFG.Viewer.prototype.removeListenerCamera=function(){
	var _this=this;
	if(_this.handler3D){
		_this.handler3D.destroy();
	}
}
;
///<jscompress sourcefile="VFGMapMessage.js" />
VFG.Viewer.prototype.cacheMessageMap=new Map();
/**
 * 处理消息
 */
VFG.Viewer.prototype.handleMessage=function(event){
	var _this=this;
	var result=JSON.parse(event.data);
	if(result && result.code && 200==result.code){
		var data=result.data;
		if('Point'==data.type){
			VFG.Point.addWebsocket(_this.viewer,result.data,_this.url)
		}
		else if('Line'==data.type){
			
		}
		else if('Polygon'==data.type){
			
		}
		else {
			console.log("未知",data.type);
		}
	}
}
;
///<jscompress sourcefile="VFGMapModel.js" />
VFG.Viewer.prototype.cacheModelMap=new Map();
VFG.Viewer.prototype.batchAddModelForMap=function(map,reload){
	var _this=this;
	var mapModel=new Map();
	for(var key in map){
		if(true==reload){
			_this.removeAllModel(key)
		}
		if(!_this.cacheModelMap.has(key)){
			for(var i=0;i<map[key].length;i++){
				var model=map[key][i];
				VFG.Model.addModel(_this.viewer,model);
			}
			if(map[key] && map[key].length>0){
				mapModel.set(key,map[key]);
			}
		}else{
			mapModel.set(key,map[key]);
		}
	}
	_this.cacheModelMap.forEach(function(value,key){
		if(!mapModel.has(key)){
			for(var i=0;i<value.length;i++){
				VFG.Model.removeById(value[i].id);
			}
		}
	});
	_this.cacheModelMap=mapModel;
}

VFG.Viewer.prototype.showOrHideModel=function(layerId,state){
	var _this=this;
	if(!_this.cachePointMap.has(layerId)){
	    this.ajaxFunc(_this.url+"/api/model/list",{sceneId:_this.sceneId,layerId:layerId}, "json", function (res){
	    	if (undefined!=res && 200==res.code) {
	    		var data=res.data;
	    		for(var i=0;i<data.length;i++){
	    			var primitive=VFG.Model.getById(data[i].id);
	    			if(primitive){
	    				VFG.Model.showOrHideById(data[i].id.id, state);
	    			}else{
	    				VFG.Model.addModel(_this.viewer,model);
	    				VFG.Model.showOrHideById(data[i].id.id, state);
	    			}
	    		}
	    		if(data!=null && data.length>0){
	    			_this.cacheModelMap.set(layerId,data);
	    		}
	        }
	    });
	}else{
		var models=this.cacheModelMap.get(layerId);
		for(var i=0;i<models.length;i++){
			VFG.Model.showOrHideById(models[i].id, state);
		}
	}
}

VFG.Viewer.prototype.removeModel=function(modelId){
	VFG.Model.removeById(modelId);
	var primitive=VFG.Model.getById(modelId);
	if(primitive){
		if(this.cacheModelMap.has(primitive.layerId)){
			var models=this.cacheModelMap.get(primitive.layerId);
			var modelLast=[];
			for(var i=0;i<models.length;i++){
				if(pointId!=models[i].id){
					modelLast.push(models[i]);
				}
			}
			this.cacheModelMap.set(primitive.layerId,modelLast);
		}
	}
}

VFG.Viewer.prototype.removeAllModel=function(layerId){
	if(this.cacheModelMap.has(layerId)){
		var models=this.cacheModelMap.get(layerId);
		for(var i=0;i<models.length;i++){
			VFG.Model.removeById(models[i].id);
		}
		this.cacheModelMap.delete(layerId);
	}
};
///<jscompress sourcefile="VFGMapPage.js" />
VFG.Viewer.prototype.cachePageMap=new Map();

VFG.Viewer.prototype.currentPageId="";
VFG.Viewer.prototype.currentFilter="";

/**
 * 根据
 */
VFG.Viewer.prototype.getPageSrcByCode=function(option){
	var menu=this.getSceneMenuByCode(option.code);
	if(menu){
		option.pageId=menu.id;
		this.getPageSrcById(option);
	}
}


/**
 * 根据获取页面资源
 */
VFG.Viewer.prototype.getPageSrcById=function(option){
	var _this=this;
	if(_this.currentPageId==option.pageId){
		if(option.progress){
			option.progress('渲染完成！');
		}
		return;
	}else{
		_this.currentPageId=option.pageId;
		var reload=(_this.currentFilter==option.filter)?false:true
		if(_this.cachePageMap.has(option.pageId)){
			var data=_this.cachePageMap.get(option.pageId);
			if(option.progress){
				option.progress('获取页面资源成功，开始渲染！');
			}
			var Point=data.Point;
			var Line=data.Line;
			var Polygon=data.Polygon;
			var Model=data.Model;
			var Map=data.Map||null;
			_this.batchAddProviderForMap(Map);
			_this.batchAddPointForMap(Point,reload);
			_this.batchAddPolylineForMap(Line);
			_this.batchAddModelForMap(Model);
			_this.batchAddPolygonForMap(Polygon);
			
			if(option.progress){
				option.progress('渲染完成！');
			}
			_this.currentFilter=option.filter;
		}else{
			if(option.progress){
				option.progress('开始加载页面资源！');
			}
			_this.ajaxFunc(_this.url+"/api/scene/getPageSrcById",{sceneId:_this.sceneId,pageId:option.pageId,filter:option.filter}, "json", function(res){
		    	 if (undefined!=res && 200==res.code) {
		    			if(option.progress){
		    				option.progress('获取页面资源成功，开始渲染！');
		    			}
		    			_this.cachePageMap.has(option.pageId,res.data)
		    			var data=res.data;
		    			var Point=data.Point;
		    			var Line=data.Line;
		    			var Polygon=data.Polygon;
		    			var Model=data.Model;
		    			var Map=data.Map||null;
		    			//资源加载
		    			_this.batchAddProviderForMap(Map);
		    			_this.batchAddPointForMap(Point);
		    			_this.batchAddPolylineForMap(Line);
		    			_this.batchAddModelForMap(Model);
		    			_this.batchAddPolygonForMap(Polygon);
		    			if(option.progress){
		    				option.progress('渲染完成！');
		    			}
		    		 if(undefined==res){
		     			if(option.progress){
		    				option.progress('资源服务异常！');
		    			}
		    		 }else{
		      			if(option.progress){
		    				option.progress(res.message);
		    			}
		    		 }
		    	 }
			})
		}
		
		//可以改装异步
		this.removePageSrcById(option);
	}
}

/**
 * 移出页面资源
 */
VFG.Viewer.prototype.removePageSrcById=function(option){
	var _this=this;
	var pageId=option.pageId;
	if(_this.cachePageMap.has(pageId)){
		var data=_this.cachePageMap.get(pageId);
		var Point=data.Point;
		var Line=data.Line;
		var Polygon=data.Polygon;
		var Model=data.Model;
		var Map=data.Map||null;
	}else{
		_this.ajaxFunc(_this.url+"/api/scene/getPageSrcById",{sceneId:_this.sceneId,pageId:pageId}, "json", function(res){
	    	 if (undefined!=res && 200==res.code) {
	    			var data=res.data;
	    			var Point=data.Point;
	    			var Line=data.Line;
	    			var Polygon=data.Polygon;
	    			var Model=data.Model;
	    			var Map=data.Map||null;
	    	 }
		})
	}
}

;
///<jscompress sourcefile="VFGMapPoint.js" />
VFG.Viewer.prototype.loadAllPoint=function(){
	var _this=this;
	 _this.ajaxFunc(_this.url+"/api/point/list",{sceneId:_this.sceneId}, "json", function(res){
		 if (undefined!=res && 200==res.code) {
			 var list=res.data;
			 for(var i=0;i<list.length;i++){
				 VFG.Point.addPrimitive(_this.viewer,list[i],_this.url);
			 }
		 }
	 });
}

/**
 * 通过Id飞行
 */
VFG.Viewer.prototype.flyToPointById=function(id){
	var _this=this;
	_this.getPointForInfo(id,function(e){
		if(e.cameraX && e.cameraY && e.cameraZ){
			_this.viewer.camera.flyTo({
			    destination : new Cesium.Cartesian3(e.cameraX*1,e.cameraY*1, e.cameraZ*1),
			    orientation : {
			        heading : e.heading*1,
			        pitch : e.pitch*1,
			        roll : e.roll*1
			    }
			});
		}else{
			if(e.x && e.y && e.z){
				_this.viewer.camera.flyTo({
				    destination : Cesium.Cartesian3.fromDegrees(e.x*1, e.y*1, e.z*1+100)
				});
			}
		}
	})
}

/**
 * 获取点
 */
VFG.Viewer.prototype.getPointForInfo=function(id,callback){
    this.ajaxFunc(this.url+"/biz/marker/point/getById",{id:id}, "json", function (res){
    	if (undefined!=res && 200==res.code) {
        	if(callback && res.data)callback(res.data);
        }
    });
}

/**
 * 获取点信息（点击）
 */
VFG.Viewer.prototype.getPointForClick=function(option){
    this.ajaxFunc(this.url+"/biz/marker/point/getPointById",{id:option.id,event:option.event}, "json", function (res){
    	if (undefined!=res && 200==res.code) {
    		if(option.callback){
    			option.callback(res.data)
    		}
        }
    });
}

VFG.Viewer.prototype.getPointPropertyForClick=function(option){
    this.ajaxFunc(this.url+"/api/point/getPropertyById",{id:option.id,event:option.event}, "json", function (res){
    	if (undefined!=res && 200==res.code) {
    		if(option.callback){
    			option.callback(res.data)
    		}
        }
    });
}

/**
 * 获取点样式(消息推送时获取数据库配置再更新图标)
 */
VFG.Viewer.prototype.getPointForStyle=function(id,type){
    var res = common_ajax.ajaxFunc(this.url+"/biz/marker/point/getPointForStyle",{id:id,type:type}, "json", null);
    if (undefined!=res && 200==res.code) {
    	return data;
    }
    return null;
}

/*****************************************************************控制页面**************************************************************************/
VFG.Viewer.prototype.cachePointMap=new Map();
/**
 * 根据页面加载点
 */
VFG.Viewer.prototype.batchAddPointForMap=function(map,reload){
	var _this=this;
	var mapPoint=new Map();
	for(var key in map){
		if(true==reload){
			_this.removeAllPoint(key)
		}
		if(!_this.cachePointMap.has(key)){
			var menu=_this.SCENE_MENU_MAP_ID[key];
			console.log(menu);
			for(var i=0;i<map[key].length;i++){
				var point=map[key][i];
				VFG.Point.addPrimitive(_this.viewer,{
					point:point,
					style:_this.POINT_STYLE[point.defaultStyleId]
				},_this.url);
			}
			if(map[key] && map[key].length>0){
				mapPoint.set(key,map[key]);
			}
		}else{
			mapPoint.set(key,map[key]);
		}
	}
	_this.cachePointMap.forEach(function(value,key){
		if(!mapPoint.has(key)){
			for(var i=0;i<value.length;i++){
				VFG.Point.removePrimitiveById(value[i].id);
			}
		}
	});
	_this.cachePointMap=mapPoint;
}

/**
 * 显示或隐藏
 */
VFG.Viewer.prototype.showOrHidePoint=function(layerId,state){
	var _this=this;
	if(!_this.cachePointMap.has(layerId)){
	    this.ajaxFunc(_this.url+"/api/point/list",{sceneId:_this.sceneId,layerId:layerId}, "json", function (res){
	    	if (undefined!=res && 200==res.code) {
	    		var data=res.data;
	    		for(var i=0;i<data.length;i++){
	    			var primitive=VFG.Point.getPrimitiveById(data[i].id);
	    			if(primitive){
	    				VFG.Point.showOrHidePrimitiveById(data[i].id, state);
	    			}else{
	    				VFG.Point.addPrimitive(_this.viewer,{
	    					point:data[i],
	    					style:_this.POINT_STYLE[data[i].defaultStyleId]
	    				},_this.url);
	    				VFG.Point.showOrHidePrimitiveById(data[i].id, state);
	    			}
	    		}
	    		if(data!=null && data.length>0){
	    			_this.cachePointMap.set(layerId,data);
	    		}
	        }
	    });
	}else{
		var points=this.cachePointMap.get(layerId);
		for(var i=0;i<points.length;i++){
			VFG.Point.showOrHidePrimitiveById(points[i].id, state);
		}
	}
}

/**
 * 移除全部
 */
VFG.Viewer.prototype.removeAllPoint=function(layerId){
	if(this.cachePointMap.has(layerId)){
		var points=this.cachePointMap.get(layerId);
		for(var i=0;i<points.length;i++){
			VFG.Point.removePrimitiveById(points[i].id);
		}
		this.cachePointMap.delete(layerId);
	}
}

/**
 * 移除点
 */
VFG.Viewer.prototype.removePoint=function(pointId){
	VFG.Point.removePrimitiveById(pointId);
	var primitive=VFG.Point.getPrimitiveById(pointId);
	if(primitive){
		if(this.cachePointMap.has(primitive.layerId)){
			var points=this.cachePointMap.get(primitive.layerId);
			var pointsLast=[];
			for(var i=0;i<points.length;i++){
				if(pointId!=points[i].id){
					pointsLast.push(points[i]);
				}
			}
			this.cachePointMap.set(primitive.layerId,pointsLast);
		}
	}
}

/**
 * 更改样式
 */
VFG.Viewer.prototype.changePointPrimitiveStyle=function(id,event){
	var _this=this;
	 var point=VFG.Point.getPrimitiveById(id);
	 if(point!=null && point.hoverStyleId){
		 if('DEFAULT'==event){
			 VFG.Point.removePrimitiveById(point.id);
			 VFG.Point.addPrimitive(_this.viewer,{
				point:point,
				style:_this.POINT_STYLE[point.defaultStyleId]
			 },_this.url);
		 }
		 else if('HOVER'==event && point.hoverStyleId){
			 VFG.Point.removePrimitiveById(point.id);
			 VFG.Point.addPrimitive(_this.viewer,{
				point:point,
				style:_this.POINT_STYLE[point.hoverStyleId]
			 },_this.url);
		 }
		 else if('SELECTED'==event && point.selectedStyleId){
			 VFG.Point.removePrimitiveById(point.id);
				VFG.Point.addPrimitive(_this.viewer,{
					point:point,
					style:_this.POINT_STYLE[point.selectedStyleId]
				},_this.url);
		 }else{
			 VFG.Point.removePrimitiveById(point.id);
			 VFG.Point.addPrimitive(_this.viewer,{
				point:point,
				style:_this.POINT_STYLE[point.defaultStyleId]
			 },_this.url);
		 }
	 }
}
;
///<jscompress sourcefile="VFGMapPolygon.js" />
/**
 * 通过Id飞行
 */
VFG.Viewer.prototype.flyToPolygonById=function(id){
	var _this=this;
	_this.getPolygonForInfo(id,function(e){
		if(e.cameraX && e.cameraY && e.cameraZ){
			_this.viewer.camera.flyTo({
			    destination : new Cesium.Cartesian3(e.cameraX*1,e.cameraY*1, e.cameraZ*1),
			    orientation : {
			        heading : e.heading*1,
			        pitch : e.pitch*1,
			        roll : e.roll*1
			    }
			});
		}
	})
}

/**
 * 获取点
 */
VFG.Viewer.prototype.getPolygonForInfo=function(id,callback){
    this.ajaxFunc(this.url+"/biz/marker/polygon/getById",{id:id}, "json", function (res){
    	if (undefined!=res && 200==res.code) {
        	if(callback && res.data)callback(res.data);
        }
    });
}

/**********************************************************************************************************/
VFG.Viewer.prototype.cachePolygonMap=new Map();
/**
 * 添加面
 */
VFG.Viewer.prototype.batchAddPolygonForMap=function(map){
	var _this=this;
	var mapPolygon=new Map();
	for(var key in map){
		if(!_this.cachePolygonMap.has(key)){
			for(var i=0;i<map[key].length;i++){
				var point=map[key][i];
				VFG.Polygon.addEntityForAPI({
					polygon:point,
					style:_this.POLYGON_STYLE[point.defaultStyleId]
				},_this.url);
			}
			if(map[key] && map[key].length>0){
				mapPolygon.set(key,map[key]);
			}
		}else{
			mapPolygon.set(key,map[key]);
		}
	}
	_this.cachePolygonMap.forEach(function(value,key){
		if(!mapPolygon.has(key)){
			for(var i=0;i<value.length;i++){
				VFG.Polygon.removeEntityById(value[i].id);
			}
		}
	});
	_this.cachePolygonMap=mapPolygon;
}

VFG.Viewer.prototype.showOrHidePolygon=function(layerId,state){
	var _this=this;
	if(!_this.cachePolygonMap.has(layerId)){
	    this.ajaxFunc(_this.url+"/api/polygon/list",{sceneId:_this.sceneId,layerId:layerId}, "json", function (res){
	    	if (undefined!=res && 200==res.code) {
	    		var data=res.data;
	    		for(var i=0;i<data.length;i++){
	    			VFG.Polygon.showOrHideEntityById(data[i].id,state);
	    		}
	    		if(data!=null && data.length>0){
	    			_this.cachePolygonMap.set(layerId,data);
	    		}
	        }
	    });
	}else{
		var points=this.cachePolygonMap.get(layerId);
		for(var i=0;i<points.length;i++){
			VFG.Polygon.showOrHideEntityById(points[i].id, state);
		}
	}
}


VFG.Viewer.prototype.changePolygonEntityStyle=function(id,event){
	var _this=this;
	 var polygon=VFG.Polygon.getPrimitiveById(id);
	 if(polygon!=null && polygon.hoverStyleId){
		 if('DEFAULT'==event){
			 VFG.Polygon.removeEntityById(polygon.id);
			 VFG.Polygon.addEntityForAPI({
				polygon:polygon,
				style:_this.POLYGON_STYLE[polygon.defaultStyleId]
			 },_this.url);
		 }
		 else if('HOVER'==event && polygon.hoverStyleId){
			 VFG.Polygon.removeEntityById(polygon.id);
				VFG.Polygon.addEntityForAPI({
					polygon:polygon,
					style:_this.POLYGON_STYLE[polygon.hoverStyleId]
				},_this.url);
		 }
		 else if('SELECTED'==event && polygon.selectedStyleId){
			 VFG.Polygon.removeEntityById(polygon.id);
				VFG.Polygon.addEntityForAPI({
					polygon:polygon,
					style:_this.POLYGON_STYLE[polygon.selectedStyleId]
				},_this.url);
		 }else{
			 VFG.Polygon.removeEntityById(polygon.id);
			 VFG.Polygon.addEntityForAPI({
				polygon:polygon,
				style:_this.POLYGON_STYLE[polygon.defaultStyleId]
			 },_this.url);
		 }
	 }
};
///<jscompress sourcefile="VFGMapPolyline.js" />
VFG.Viewer.prototype.cachePolylineMap=new Map();
VFG.Viewer.prototype.batchAddPolylineForMap=function(map){
	var _this=this;
	var mapPolyline=new Map();
	for(var key in map){
		if(!_this.cachePolylineMap.has(key)){
			for(var i=0;i<map[key].length;i++){
				var point=map[key][i];
				var polyline=map[key][i];
				VFG.Polyline.addEntityForAPI({
					polyline:polyline,
					style:_this.LINE_STYLE[polyline.defaultStyleId]
				},_this.url);
			}
			if(map[key] && map[key].length>0){
				mapPolyline.set(key,map[key]);
			}
		}else{
			mapPolyline.set(key,map[key]);
		}
	}
	_this.cachePolylineMap.forEach(function(value,key){
		if(!mapPolyline.has(key)){
			for(var i=0;i<value.length;i++){
				VFG.Polyline.removeEntityById(value[i].id);
			}
		}
	});
	_this.cachePolylineMap=mapPolyline;
}

VFG.Viewer.prototype.showOrHidePolyline=function(layerId,state){
	var _this=this;
	if(!_this.cachePolylineMap.has(layerId)){
	    this.ajaxFunc(_this.url+"/api/line/list",{sceneId:_this.sceneId,layerId:layerId}, "json", function (res){
	    	if (undefined!=res && 200==res.code) {
	    		var data=res.data;
	    		for(var i=0;i<data.length;i++){
	    			VFG.Polyline.showOrHideEntityById(data[i].id,state);
	    		}
	    		if(data!=null && data.length>0){
	    			_this.cachePolylineMap.set(layerId,data);
	    		}
	        }
	    });
	}else{
		var lines=this.cachePolylineMap.get(layerId);
		for(var i=0;i<lines.length;i++){
			VFG.Polyline.showOrHideEntityById(lines[i].id, state);
		}
	}
}

VFG.Viewer.prototype.changePolylineEntityStyle=function(id,event){
	var _this=this;
	 var polyline=VFG.Polyline.getPrimitiveById(id);
	 if(polyline!=null && polyline.hoverStyleId){
		 if('DEFAULT'==event){
			 VFG.Polyline.removeEntityById(polyline.id);
			 VFG.Polyline.addEntityForAPI({
				polyline:polyline,
				style:_this.LINE_STYLE[polyline.defaultStyleId]
			 },_this.url);
		 }
		 else if('HOVER'==event && polyline.hoverStyleId){
			 VFG.Polyline.removeEntityById(polyline.id);
			 VFG.Polyline.addEntityForAPI({
				polyline:polyline,
				style:_this.LINE_STYLE[polyline.hoverStyleId]
			 },_this.url);
		 }
		 else if('SELECTED'==event && polyline.selectedStyleId){
			 VFG.Polyline.removeEntityById(polyline.id);
			 VFG.Polyline.addEntityForAPI({
				polyline:polyline,
				style:_this.LINE_STYLE[polyline.selectedStyleId]
			 },_this.url);
		 }else{
			 VFG.Polyline.removeEntityById(polyline.id);
			 VFG.Polyline.addEntityForAPI({
				polyline:polyline,
				style:_this.LINE_STYLE[polyline.defaultStyleId]
			 },_this.url);
		 }
	 }
};
///<jscompress sourcefile="VFGMapProvider.js" />
VFG.Viewer.prototype.cacheProviderMap=new Map();
/**
 * 批量添加Provider
 */
VFG.Viewer.prototype.batchAddProviderForMap=function(map){
	var _this=this;
	var mapProvider=new Map();
	for(var key in map){
		if(_this.cacheProviderMap.has(key)){
			mapProvider.set(key,map[key]);
		}else{
			if(map[key]){
				for(var i=0;i<map[key].length;i++){
					var provider=map[key][i];
					if(!VFG.Provider.Map.has(provider.id) && provider.show=='1'){
						if('terrain'==provider.dataType){
							var terrainProvider=VFG.Provider.getTerrainProviderFromServ(provider);
							if(terrainProvider){
								VFG.Provider.hasTerrain=true;
								_this.viewer.terrainProvider=terrainProvider;
								VFG.Provider.Map.set(provider.id,terrainProvider);
							}
						}else{
							var imageryProvider=VFG.Provider.getImageryProviderFromServ(provider);
							if(imageryProvider){
								var sImgPro=_this.viewer.imageryLayers.addImageryProvider(imageryProvider);
								VFG.Provider.Map.set(provider.id,sImgPro);
							}
						}
					}
				}
			}
			if(map[key] && map[key].length>0){
				mapProvider.set(key,map[key]);
			}
		}
	}
	_this.cacheProviderMap.forEach(function(value,key){
		if(!mapProvider.has(key)){
			for(var i=0;i<value.length;i++){
				var provider=value[i];
				if('terrain'==provider.dataType){
					VFG.Provider.removeTerrainProviderById(_this.viewer,provider.id);
				}else{
					VFG.Provider.removeById(_this.viewer,provider.id);
				}
			}
		}
	});
	_this.cacheProviderMap=mapProvider;
}


/**
 * 移除图层 bug存在后期修复
 */
VFG.Viewer.prototype.removeProvider=function(id){
	var _this=this;
 	_this.cacheProviderMap.forEach(function(value,key){
		for(var i=0;i<value.length;i++){
			var provider=value[i];
			if(provider.id==id){
				if('terrain'==provider.dataType){
					VFG.Provider.removeTerrainProviderById(_this.viewer,provider.id);
				}else{
					VFG.Provider.removeById(_this.viewer,provider.id);
				}
				value.splice(i,1); 
				if(value.length==0){
					_this.cacheProviderMap.delete(key);
				}
				return;
			}
		}
	});
}

VFG.Viewer.prototype.showOrHideProvider=function(layerId,state){
	var _this=this;
	if(false==state){
		_this.removeProvider(layerId);
	}else{
		if(!_this.cacheProviderMap.has(layerId)){
			_this.ajaxFunc(_this.url+"/api/map/list",{sceneId:_this.sceneId,layerId:layerId}, "json", function (res){
		    	if (undefined!=res && 200==res.code) {
		    		var data=res.data;
		    		for(var i=0;i<data.length;i++){
						var provider=data[i];
						if(!VFG.Provider.Map.has(provider.id) && provider.show=='1'){
							if('terrain'==provider.dataType){
								var terrainProvider=VFG.Provider.getTerrainProviderFromServ(provider);
								if(terrainProvider){
									VFG.Provider.hasTerrain=true;
									_this.viewer.terrainProvider=terrainProvider;
									VFG.Provider.Map.set(provider.id,terrainProvider);
								}
							}else{
								var imageryProvider=VFG.Provider.getImageryProviderFromServ(provider);
								if(imageryProvider){
									var sImgPro=_this.viewer.imageryLayers.addImageryProvider(imageryProvider);
									VFG.Provider.Map.set(provider.id,sImgPro);
								}
							}
						}
		    		}
		    		if(data!=null && data.length>0){
		    			_this.cacheProviderMap.set(layerId,data);
		    		}
		        }
		    });
		}
	}
}
;
///<jscompress sourcefile="VFGMapRequst.js" />
/**
 * url:服务器
 * param:参数
 * reqType：请求类型（get/post）
 * dataType：返回数据格式（get/post）
 * async：是否异步
 * callback：回调函数
 */
VFG.Viewer.prototype.ajaxFunc = function(url, data, dataType, callback){
	if(dataType == undefined || dataType == null){
		dataType = "html";
	}
	var result;
	$.ajax({
		type : "post",
		url : encodeURI(encodeURI(url)),
		data : data,
		dataType : dataType,
		contentType: "application/x-www-form-urlencoded; charset=UTF-8",
		async: true,
		cache: false,
		success:function(response){
			result = response;
			//扩展回调函数
			if( callback != null ){
				callback(response);
			}
		},
		error:function(response){
			if( callback != null ){
				callback(response);
			}
		}
	});
	return result;
};
;
///<jscompress sourcefile="VFGMapScene.js" />
/**
 * 场景默认视角
 * id:场景id
 */
VFG.Viewer.prototype.flyToHome=function(){
	if(this.scene){
		if(this.scene.cameraX*1 && this.scene.cameraY*1 && this.scene.cameraZ*1){
			this.viewer.scene.camera.flyTo({
			    duration:1,
				destination: new Cesium.Cartesian3(this.scene.cameraX*1,this.scene.cameraY*1,this.scene.cameraZ*1),
				orientation:{
					heading:this.scene.heading*1,
					pitch: this.scene.pitch*1,
					roll: this.scene.roll*1,
				}
			});
		}
	}
}

/**
 * 切换菜单视角
 */
VFG.Viewer.prototype.flyToMenu=function(option){
	var _this=this;
    this.ajaxFunc(this.url+"/biz/scene/menu/getBizSceneMenuById",{id:option.id}, "json", function(res){
    	 if (undefined!=res && 200==res.code) {
    		 var data=res.data;
    		 if(data){
				if(data.cameraX*1 && data.cameraY*1 && data.cameraZ*1){
					_this.viewer.scene.camera.flyTo({
					    duration:1,
						destination: new Cesium.Cartesian3(data.cameraX*1,data.cameraY*1,data.cameraZ*1),
						orientation:{
							heading:data.heading*1,
							pitch: data.pitch*1,
							roll: data.roll*1,
						}
					});
				}
    		 }
    		 if(option.callback){
    			 option.callback(res);
    		 }
    	 }else{
    		 if(option.callback){
    			 option.callback(res);
    		 }
    	 }
    });
}

/**
 * 飞至点
 */
VFG.Viewer.prototype.flyToPoint=function(option){
	var _this=this;
    this.ajaxFunc(this.url+"/biz/scene/findById",{id:option.id}, "json", function(res){
    	 if (undefined!=res && 200==res.code) {
    		 var res=res.data
    		 if(data){
				if(data.cameraX*1 && data.cameraY*1 && data.cameraZ*1){
					_this.viewer.scene.camera.flyTo({
					    duration:1,
						destination: new Cesium.Cartesian3(data.cameraX*1,data.cameraY*1,data.cameraZ*1),
						orientation:{
							heading:data.heading*1,
							pitch: data.pitch*1,
							roll: data.roll*1,
						}
					});
				}
    		 }
    		 if(option.callback){
    			 option.callback(res);
    		 }
    	 }else{
    		 if(option.callback){
    			 option.callback(res);
    		 }
    	 }
    });
}

/**
 * 图层隐藏
 * param:{
 * 	id:图层id(图层树节点id)
 * }
 * 
 */
VFG.Viewer.prototype.hideLayer=function(id){
	var _this=this;
	_this.getLayerForInfo(id,function (res){
		if (undefined!=res && 200==res.code) {
			VFG.Point.showOrHidePrimitiveById(res.data.id,false);
			_this.getLayerForParentId(res.data.id,function(e){
				if (undefined!=e && 200==e.code) {
					for(layer of e.data){
						VFG.Point.showOrHidePrimitiveById(layer.id,false);
					}
			    }
			});
	    }
	});
}

/**
 * 图层显示
 * param:{
 * 	id:图层id(图层树节点id)
 * }
 * 
 */
VFG.Viewer.prototype.showLayer=function(id){
	var _this=this;
	_this.getLayerForInfo(id,function (res){
		if (undefined!=res && 200==res.code) {
			VFG.Point.showOrHidePrimitiveById(res.data.id,true);
			_this.getLayerForParentId(res.data.id,function(e){
				if (undefined!=e && 200==e.code) {
					for(layer of e.data){
						VFG.Point.showOrHidePrimitiveById(layer.id,true);
					}
			    }
			});
	    }
	});
}

VFG.Viewer.prototype.hideLayerByCode=function(code){
	var _this=this;
	_this.getLayerForInfoByCode(code,function (res){
		if (undefined!=res && 200==res.code) {
			for(item of res.date){
				VFG.Point.showOrHidePrimitiveById(item.id,false);
				_this.getLayerForParentId(item.id,function(e){
					if (undefined!=e && 200==e.code) {
						for(layer of e.data){
							VFG.Point.showOrHidePrimitiveById(layer.id,false);
						}
				    }
				});
			}
	    }
	});
}

VFG.Viewer.prototype.showLayerByCode=function(code){
	var _this=this;
	_this.getLayerForInfoByCode(code,function (res){
		if (undefined!=res && 200==res.code) {
			for(item of res.data){
				VFG.Point.showOrHidePrimitiveById(item.id,true);
				_this.getLayerForParentId(item.id,function(e){
					if (undefined!=e && 200==e.code) {
						for(layer of e.data){
							VFG.Point.showOrHidePrimitiveById(layer.id,true);
						}
				    }
				});
			}
	    }
	});
}

VFG.Viewer.prototype.showLayerAll=function(){
	VFG.Point.LabelMap.forEach(function(value,key){
		value.show=true;
	});
	VFG.Point.PointMap.forEach(function(value,key){
		value.show=true;
	});
	VFG.Point.BillboardMap.forEach(function(value,key){
		value.show=true;
	});
}

VFG.Viewer.prototype.hideLayerAll=function(){
	VFG.Point.LabelMap.forEach(function(value,key){
		value.show=false;
	});
	VFG.Point.PointMap.forEach(function(value,key){
		value.show=false;
	});
	VFG.Point.BillboardMap.forEach(function(value,key){
		value.show=false;
	});
}

/**
 * 获取场景
 */
VFG.Viewer.prototype.getLayerForInfo=function(id,callback){
    this.ajaxFunc(this.url+"/biz/layer/getLayerById",{id:id}, "json", function(res){
    	if(callback)callback(res);
    });
}

VFG.Viewer.prototype.getLayerForInfoByCode=function(code,callback){
    this.ajaxFunc(this.url+"/biz/layer/getLayerByCode",{code:code}, "json", function(res){
    	if(callback)callback(res);
    });
}

VFG.Viewer.prototype.getLayerForParentId=function(parentId,callback){
    this.ajaxFunc(this.url+"/biz/layer/getLayerByParentId",{parentId:parentId}, "json", function(res){
    	if(callback)callback(res);
    });
}
;
///<jscompress sourcefile="VFGMapUtil.js" />
/**
 * 获取UUID
 */
VFG.Viewer.prototype.getUuid = function() {
	var s = [];
	var hexDigits = "0123456789abcdef";
	for (var i = 0; i < 36; i++) {
		s[i] = hexDigits.substr(Math.floor(Math.random() * 0x10), 1);
	}
	s[14] = "4"; 
	s[19] = hexDigits.substr((s[19] & 0x3) | 0x8, 1); 
	s[8] = s[13] = s[18] = s[23] = "-";
	var uuid = s.join("");
	return uuid;
};

/**
 * 笛卡尔坐标转经纬度
 */
VFG.Viewer.prototype.getLnLaFormC3  = function(cartesian3) {
	return VFG.Util.getC3ToLnLa(this.viewer, cartesian3)
}

/**
 * 经纬度装屏幕坐标
 * position:{
 * 	x:经度
 *  y:维度
 *  z:高度
 * }
 */
VFG.Viewer.prototype.getC2FormLnLa = function(position) {
	return Cesium.SceneTransforms.wgs84ToWindowCoordinates(this.viewer.scene,this.getC3FormLnLa(position))
}

/**
 * 经纬度转笛卡尔坐标
 * position:{
 * 	x:经度
 *  y:维度
 *  z:高度
 * }
 */
VFG.Viewer.prototype.getC3FormLnLa = function(position) {
	return Cesium.Cartesian3.fromDegrees(position.x*1,position.y*1,position.z*1);
}


/**
 * Turf多边形
 */
VFG.Viewer.prototype.getTurfPolygon = function (points) {
	return VFG.Util.getTurfPolygon(points);
}

/**
 * Turf点
 */
VFG.Viewer.prototype.getTurfPoint = function (point) {
	return VFG.Util.getTurfPoint(point);
}

/**
 * 点是否在多边形内部
 */
VFG.Viewer.prototype.booleanPointInPolygon = function (polygon,point) {
	return VFG.Util.booleanPointInPolygon(polygon, point);
}

/**
 * 多边形内的点
 */
VFG.Viewer.prototype.getPointInPolygon = function (polygonPoints,points) {
	var polygon =VFG.Util.getTurfPolygon(polygonPoints);
	var inPoints=[];
	for(var i=0;i<points.length;i++){
		if(VFG.Util.booleanPointInPolygon(polygon, VFG.Util.getTurfPoint(points[i]))){
			inPoints.push(points[i]);
		}
	}
	return inPoints;
}
;
///<jscompress sourcefile="VFGMapWebSocket.js" />
VFG.Viewer.prototype.openWebSocket=function(options){
	var _this=this;
	_this.webSocket=new VFG.WebSocket({
		id:_this.getUuid(),
		ws:options.ws,
		onopen:function(){
			console.log('开启WebSocket服务!!!');
			if(options.onopen)  options.onopen();
		},
		onmessage:function(event){
			_this.handleWebSocket(event);
			if(options.onmessage)  options.onmessage(event);
		},
		onclose:function(){
			_this.webSocket=null;
			console.log('关闭WebSocket服务!!!');
			if(options.onclose)  options.onclose();
		},
		onerror:function(e){
			if(options.onerror)  options.onerror();
		},
	});
}

VFG.Viewer.prototype.closeWebSocket=function(option){
	var _this=this;
	if(_this.webSocket){
		_this.webSocket.destroy();
		_this.webSocket=null;
	}
}

VFG.Viewer.prototype.sendMessageByWebSocket=function(message){
	var _this=this;
	if(_this.webSocket){
		_this.webSocket.send(message);
	}
}

/**
 * 处理后端事件
 */
VFG.Viewer.prototype.handleWebSocket=function(event){
	var _this=this;
	var result=JSON.parse(event.data);
	if(result && result.code && 200==result.code){
		var data=result.data;
		console.log("data",data);
		if('Point'==data.type){
			VFG.Point.addWebsocket(_this.viewer,result.data,_this.url)
		}
		else if('Line'==data.type){
			
		}
		else if('Polygon'==data.type){
			
		}
		else {
			console.log("未知",data.type);
		}
	}
	console.log(event);
}
;
///<jscompress sourcefile="VFGMouseEvent.js" />
VFG.MouseEvent=function(viewer, option){
	this.option = option;
	this.viewer = viewer;
	if(!this.viewer){
		console.log('参数必填！！！');
		return;
	}
	this.init();
}
/**
 * 初始化
 */
VFG.MouseEvent.prototype.init = function() {
	var _self = this;
	_self.handler = new Cesium.ScreenSpaceEventHandler(_self.viewer.scene.canvas);
    //左键点击操作
    _self.handler.setInputAction(function (movement) {
        var cartesian3 =VFG.Util.getScreenToC3(_self.viewer,movement.position);
        var entity = _self.viewer.scene.pick(movement.position);//选取当前的entity
        //拾取实体
        if (Cesium.defined(entity)){
	        if( _self.option.LEFT_CLICK_EN){
	        	 _self.option.LEFT_CLICK_EN(entity,movement.position);
	        }
        }
        //拾取屏幕坐标
        if (Cesium.defined(movement.position)){
	        if( _self.option.LEFT_CLICK_C2){
	        	 _self.option.LEFT_CLICK_C2(movement.position);
	        }
        }
        //拾取笛卡尔坐标
        if (Cesium.defined(cartesian3)){
	        if( _self.option.LEFT_CLICK_C3){
	        	 _self.option.LEFT_CLICK_C3(movement.position);
	        }
        }
        //拾取经纬度
        if (Cesium.defined(cartesian3)){
	        if( _self.option.LEFT_CLICK_LNLA){
	        	 _self.option.LEFT_CLICK_LNLA(VFG.Util.getC3ToLnLa(_self.viewer,cartesian3));
	        }
        }
    }, Cesium.ScreenSpaceEventType.LEFT_CLICK);
    
    //鼠标移动事件
    _self.handler.setInputAction(function (movement) {
        var cartesian3 =VFG.Util.getScreenToC3(_self.viewer,movement.endPosition);
        var entity = _self.viewer.scene.pick(movement.endPosition);//选取当前的entity
        //拾取实体
        if (Cesium.defined(entity)){
	        if( _self.option.MOUSE_MOVE_EN){
	        	 _self.option.MOUSE_MOVE_EN(entity,movement.endPosition);
	        }
        }
        //拾取屏幕坐标
        if (Cesium.defined(movement.position)){
	        if( _self.option.MOUSE_MOVE_C2){
	        	 _self.option.MOUSE_MOVE_C2(movement.endPosition);
	        }
        }
        //拾取笛卡尔坐标
        if (Cesium.defined(cartesian3)){
	        if( _self.option.MOUSE_MOVE_C3){
	        	 _self.option.MOUSE_MOVE_C3(movement.posiendPositiontion);
	        }
        }
        //拾取经纬度
        if (Cesium.defined(cartesian3)){
	        if( _self.option.MOUSE_MOVE_LNLA){
	        	 _self.option.MOUSE_MOVE_LNLA(VFG.Util.getC3ToLnLa(_self.viewer,cartesian3));
	        }
        }
    }, Cesium.ScreenSpaceEventType.MOUSE_MOVE);
    //右键点击操作
    _self.handler.setInputAction(function (click) {
    }, Cesium.ScreenSpaceEventType.RIGHT_CLICK);
};
/**
 * 销毁
 */
VFG.MouseEvent.prototype.destroy = function() {
	var _this=this;
    if( _this.option.end){
    	_this.option.end();
    };
    if( _this.handler){
    	_this.handler.destroy();
    	_this.handler = null;
    };
	delete _this.ops,
	delete _this.handler;
	return Cesium.destroyObject(_this);
};;
///<jscompress sourcefile="VFGListener.js" />
/**
 * viewer
 * option{
 * 	position:{
 * 		x:经度
 * 		y:维度
 * 		z:高度
 * 	},
 *  callBack:fun(e)回调函数
 * }
 * 
 */
VFG.Listener=function(viewer,option){
	this.option = Cesium.defaultValue(option, Cesium.defaultValue.EMPTY_OBJECT);
	if (!option) {
		console.log('参数必填!');
		return;
	}
	if (!viewer) {
		console.log('参数必填!');
		return;
	}
	this.option = option;
	this.viewer = viewer;
	this.id=option.id;
	
	this.position;
	if(VFG.Point.getPointById(this.id)){
		this.position =VFG.Point.getPointById(this.id).position.getValue();
	}else{
		this.position = Cesium.Cartesian3.fromDegrees(option.position.x*1, option.position.y*1, option.position.z*1);
	}
	
//	this.position = option.position;
	this.callBack = option.callBack;
	if(!this.position){
		console.log('参数必填!');
		return;
	}
	this.init();
}

/**
 * 初始化
 */
VFG.Listener.prototype.init=function(){
	var _this=this;
	var cartesian3=_this.position;
	if(cartesian3){
		_this.event=function(){
			var cartesian2=Cesium.SceneTransforms.wgs84ToWindowCoordinates(_this.viewer.scene, cartesian3);
			if (Cesium.defined(cartesian2)){
				if(_this.callBack){
					_this.callBack(cartesian2);
				}
			}
		}
		_this.viewer.scene.postRender.addEventListener(_this.event);
	}else{
		console.log('初始化失败，检测是否有效经纬度!!!');
	}
}

/**
 * 销毁
 */
VFG.Listener.prototype.destroy=function(){
	var _this = this;
	if(_this.event){
		_this.viewer.scene.postRender.removeEventListener(_this.event);
	}
	delete this.option,
	delete this.callBack,
	delete this.viewer,
	delete this.position;
	return Cesium.destroyObject(this);
}
;
///<jscompress sourcefile="VFGWebSocket.js" />
VFG.WebSocket=function(option){
	this.option = Cesium.defaultValue(option, Cesium.defaultValue.EMPTY_OBJECT);
	if (!option) {
		console.log('参数必填!');
		return;
	}
	this.option = option;
	this.ws = option.ws;
	this.id = option.id;
	this.onerror = option.onerror;
	this.onopen = option.onopen;
	this.onclose = option.onclose;
	this.onmessage = option.onmessage;
	this.init();
}

/**
 * 初始化
 */
VFG.WebSocket.prototype.init=function(){
	var _this=this;
	//判断当前浏览器是否支持WebSocket
	if ('WebSocket' in window) {
		_this.websocket = new WebSocket(_this.ws+'/'+_this.id+'/0');
		//连接发生错误的回调方法
		_this.websocket.onerror = function () {
		    if(_this.onerror) _this.onerror();
		};
		
		//连接成功建立的回调方法
		_this.websocket.onopen = function () {
		    if(_this.onopen) _this.onopen();
		}
		
		//接收到消息的回调方法
		_this.websocket.onmessage = function (event) {
		    if(_this.onmessage) _this.onmessage(event);
		}
		
		//连接关闭的回调方法
		_this.websocket.onclose = function () {
		    if(_this.onclose) _this.onclose();
		}
	}
	else {
		if(_this.error){
			_this.onerror('当前浏览器 Not support websocket');
		}
	}
}

/**
 * 发送消息
 */
VFG.WebSocket.prototype.send=function(message){
	var _this = this;
	if(_this.websocket){
		 websocket.send(message);
	}
}

/**
 *  关闭
 */
VFG.WebSocket.prototype.close=function(){
	var _this = this;
	if(_this.websocket){
		 websocket.close();
	}
}

/**
 * 销毁
 */
VFG.WebSocket.prototype.destroy=function(){
	var _this = this;
	if(_this.websocket){
		 websocket.close();
	}
	return Cesium.destroyObject(this);
}
;
///<jscompress sourcefile="PolylineTrailLinkMaterialProperty.js" />
//定义流动线
function initPolylineTrailLinkMaterialProperty(data) {
    function PolylineTrailLinkMaterialProperty(color, duration) {
        this._definitionChanged = new Cesium.Event();
        this._color = undefined;
        this._colorSubscription = undefined;
        this.color = color;
        this.duration = duration;
        this._time = (new Date()).getTime();
    }
    Object.defineProperties(PolylineTrailLinkMaterialProperty.prototype, {
        isConstant: {
            get: function () {
                return false;
            }
        },
        definitionChanged: {
            get: function () {
                return this._definitionChanged;
            }
        },
        color: Cesium.createPropertyDescriptor('color')
    });
    PolylineTrailLinkMaterialProperty.prototype.getType = function (time) {
        return 'PolylineTrailLink'+data.type;
    }
    PolylineTrailLinkMaterialProperty.prototype.getValue = function (time, result) {
        if (!Cesium.defined(result)) {
            result = {};
        }
        result.color = Cesium.Property.getValueOrClonedDefault(this._color, time, Cesium.Color.WHITE, result.color);
        result.image = Cesium.Material.PolylineTrailLinkImage;
        result.time = (((new Date()).getTime() - this._time) % this.duration) / this.duration;
        return result;
    }
    PolylineTrailLinkMaterialProperty.prototype.equals = function (other) {
        return this === other || (other instanceof PolylineTrailLinkMaterialProperty && Property.equals(this._color, other._color))
    };
    Cesium.PolylineTrailLinkMaterialProperty = PolylineTrailLinkMaterialProperty;
    Cesium.Material.PolylineTrailLinkType = 'PolylineTrailLink'+data.type;
    Cesium.Material.PolylineTrailLinkImage = ctx+'/assets/images/colors1.png';//图片
    if('0'===data.type){
        Cesium.Material.PolylineTrailLinkSource = 
        	"\
        	  uniform float time;\n\ uniform vec4 color;\n\
        	  uniform sampler2D image;\n\
        	  czm_material czm_getMaterial(czm_materialInput materialInput)\n\
        	  {\n\
        	     czm_material material = czm_getDefaultMaterial(materialInput);\n\
        	     vec2 st = materialInput.st;\n\
        	     vec4 colorImage = texture2D(image, vec2(fract(st.s-time), st.t));\n\
        	     material.alpha = colorImage.a *  color.a ;\n\
        	     material.diffuse = color.rgb;\n\
        	     return material;\n\
        	  }";
    	
    }
    else if('1'===data.type){
    	
        Cesium.Material.PolylineTrailLinkSource = 
        	"\
     	   uniform vec4 color;\n\
     	  uniform float time;\n\
     	  uniform sampler2D image;\n\
     	  czm_material czm_getMaterial(czm_materialInput materialInput)\n\
     	  {\n\
     	     czm_material material = czm_getDefaultMaterial(materialInput);\n\
     	     vec2 st = materialInput.st*10.0;\n\
     	     vec4 colorImage = texture2D(image, vec2(fract(st.s-time*10.0), fract(st.t)));\n\
     	     material.alpha = colorImage.a * color.a;\n\
     	     material.diffuse = color.rgb;\n\
     	     return material;\n\
     	  }";
    }
    else if('2'===data.type){
        Cesium.Material.PolylineTrailLinkSource = 
       	 "\
           uniform vec4 color;\n\
            uniform float time;\n\
            uniform sampler2D image;\n\
            czm_material czm_getMaterial(czm_materialInput materialInput)\n\
            {\n\
               czm_material material = czm_getDefaultMaterial(materialInput);\n\
               vec2 st = materialInput.st*10.0;\n\
               vec4 colorImage = texture2D(image, vec2(fract(st.s-time*10.0), fract(st.t)));\n\
               material.alpha = colorImage.a * color.a;\n\
               material.diffuse = color.rgb;\n\
               return material;\n\
            }";
    	
    }else {
    	
        Cesium.Material.PolylineTrailLinkSource = 
        	"\
        	  uniform float time;\n\ uniform vec4 color;\n\
        	  uniform sampler2D image;\n\
        	  czm_material czm_getMaterial(czm_materialInput materialInput)\n\
        	  {\n\
        	     czm_material material = czm_getDefaultMaterial(materialInput);\n\
        	     vec2 st = materialInput.st;\n\
        	     vec4 colorImage = texture2D(image, vec2(fract(st.s-time), st.t));\n\
        	     material.alpha = colorImage.a *  color.a ;\n\
        	     material.diffuse = color.rgb;\n\
        	     return material;\n\
        	  }";
    	
    }
    
    // material.alpha:透明度;material.diffuse：颜色;
    Cesium.Material._materialCache.addMaterial(Cesium.Material.PolylineTrailLinkType, {
        fabric: {
            type: Cesium.Material.PolylineTrailLinkType,
            uniforms: {
                color: new Cesium.Color(1.0, 0.0, 0.0, 0.5),
                image: Cesium.Material.PolylineTrailLinkImage,
                time: 0
            },
            source: Cesium.Material.PolylineTrailLinkSource
        },
        translucent: function (material) {
            return true;
        }
    })
};
///<jscompress sourcefile="WallMaterialProperty.js" />
//定义流动线
function initPolylineTrailLinkMaterialProperty(data) {
    function PolylineTrailLinkMaterialProperty(color, duration) {
        this._definitionChanged = new Cesium.Event();
        this._color = undefined;
        this._colorSubscription = undefined;
        this.color = color;
        this.duration = duration;
        this._time = (new Date()).getTime();
    }
    Object.defineProperties(PolylineTrailLinkMaterialProperty.prototype, {
        isConstant: {
            get: function () {
                return false;
            }
        },
        definitionChanged: {
            get: function () {
                return this._definitionChanged;
            }
        },
        color: Cesium.createPropertyDescriptor('color')
    });
    PolylineTrailLinkMaterialProperty.prototype.getType = function (time) {
        return 'PolylineTrailLink';
    }
    PolylineTrailLinkMaterialProperty.prototype.getValue = function (time, result) {
        if (!Cesium.defined(result)) {
            result = {};
        }
        result.color = Cesium.Property.getValueOrClonedDefault(this._color, time, Cesium.Color.WHITE, result.color);
        result.image = Cesium.Material.PolylineTrailLinkImage;
        result.time = (((new Date()).getTime() - this._time) % this.duration) / this.duration;
        return result;
    }
    PolylineTrailLinkMaterialProperty.prototype.equals = function (other) {
        return this === other || (other instanceof PolylineTrailLinkMaterialProperty && Property.equals(this._color, other._color))
    };
    Cesium.PolylineTrailLinkMaterialProperty = PolylineTrailLinkMaterialProperty;
    Cesium.Material.PolylineTrailLinkType = 'PolylineTrailLink';
    Cesium.Material.PolylineTrailLinkImage = ctx+'/assets/images/colors1.png';//图片
    Cesium.Material.PolylineTrailLinkSource = "czm_material czm_getMaterial(czm_materialInput materialInput)\n\
                                                       {\n\
                                                            czm_material material = czm_getDefaultMaterial(materialInput);\n\
                                                            vec2 st = materialInput.st;\n\
                                                            vec4 colorImage = texture2D(image, vec2(fract(st.s - time), st.t));\n\
                                                            material.alpha = colorImage.a * color.a;\n\
                                                            material.diffuse = (colorImage.rgb+color.rgb)/2.0;\n\
                                                            return material;\n\
                                                        }";
    
/*    "czm_material czm_getMaterial(czm_materialInput materialInput)\n\
    {\n\
        czm_material material = czm_getDefaultMaterial(materialInput);\n\
        vec2 st = materialInput.st;\n\
        vec4 colorImage = texture2D(image, vec2(fract((st.t - time)), st.t));\n\
        vec4 fragColor;\n\
        fragColor.rgb = (colorImage.rgb+color.rgb) / 1.0;\n\
        fragColor = czm_gammaCorrect(fragColor);\n\
        material.alpha = colorImage.a * color.a;\n\
        material.diffuse = (colorImage.rgb+color.rgb)/2.0;\n\
        material.emission = fragColor.rgb;\n\
        return material;\n\
    }";*/
    
    // material.alpha:透明度;material.diffuse：颜色;
    Cesium.Material._materialCache.addMaterial(Cesium.Material.PolylineTrailLinkType, {
        fabric: {
            type: Cesium.Material.PolylineTrailLinkType,
            uniforms: {
                color: new Cesium.Color(1.0, 0.0, 0.0, 0.5),
                image: Cesium.Material.PolylineTrailLinkImage,
                time: 0
            },
            source: Cesium.Material.PolylineTrailLinkSource
        },
        translucent: function (material) {
            return true;
        }
    })
};
///<jscompress sourcefile="VFGModel.js" />
VFG.Model=function(){
}
VFG.Model.Layers= new Cesium.PrimitiveCollection();
VFG.Model.Primitives=new Map();
VFG.Model.Resource=new Map();

VFG.Model.addModel=function(viewer,ops){
	if('GLTF'==ops.type){
		this.createGltfPrimitive(viewer,ops);
	}
	else if('3DTILES'==ops.type){
		this.create3DTilePrimitive(viewer,ops);
	}
}

VFG.Model.createGltfPrimitive=function(viewer,ops){
	if(!ops){
		console.log('参数必填!!!');
		return;
	}
	
	if(!ops.uri){
		console.log('模型地址必填!!!');
		return;
	}
	
	if('GLTF'!=ops.type){
		console.log('模型格式必需是GLTF!!!');
		return;
	}
	if(!(ops.posX && ops.posY && ops.posZ)){
		console.log('坐标必填!!!');
		return;
	}
	
	if(!this.Primitives.has(ops.id)){
		var heading = Cesium.defaultValue(ops.heading, 0.0);
	    var pitch = Cesium.defaultValue(ops.pitch, 0.0);
	    var roll = Cesium.defaultValue(ops.roll, 0.0);
	    var headingPitchRoll = new Cesium.HeadingPitchRoll(Cesium.Math.toRadians(heading), Cesium.Math.toRadians(pitch), Cesium.Math.toRadians(roll));
		var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(ops.displayNear,ops.displayFar);
		var origin = Cesium.Cartesian3.fromDegrees(ops.posX*1, ops.posY*1,ops.posZ*1);
		var modelMatrix =Cesium.Transforms.headingPitchRollToFixedFrame(origin, headingPitchRoll, Cesium.Ellipsoid.WGS84, Cesium.Transforms.eastNorthUpToFixedFrame, new Cesium.Matrix4());
		var model = this.Layers.add(Cesium.Model.fromGltf({
			id:ops.id,
			name:ops.name||'未命名',
			url: ops.uri,
			type:ops.type,
			bizType:ops.code||'',
			show : ( ops.show &&  ops.show!='1')?false : true,                     
			modelMatrix : modelMatrix,
			scale: ops.scale*1||1,
			minimumPixelSize:(ops.minimumPixelSize)?ops.minimumPixelSize*1:0,
			maximumScale:(ops.minimumPixelSize)?ops.minimumPixelSize*1:undefined,
			allowPicking : true,        
			debugShowBoundingVolume : false, 
			debugWireframe : false,
			distanceDisplayCondition:distanceDisplayCondition?distanceDisplayCondition:undefined,
		}));
		model.readyPromise.then(function(model) {
		  model.activeAnimations.addAll();
		}).otherwise(function(error){
	    });
		this.Primitives.set(ops.id,model);
		this.Resource.set(ops.id,ops);
		return model;
	}else{
		return this.Primitives.get(ops.id);
	}
}

VFG.Model.create3DTilePrimitive=function(viewer,ops){
	console.log(ops);
	if(!ops){
		console.log('参数必填!!!');
		return;
	}
	
	if(!ops.uri){
		console.log('模型地址必填!!!');
		return;
	}
	
	if('3DTILES'!=ops.type){
		console.log('模型格式必需是3DTILES!!!');
		return;
	}
	
	if(!this.Primitives.has(ops.id)){
		var primitive=this.Layers.add(new Cesium.Cesium3DTileset({
			id : ops.id,
			url : ops.uri,
			name : ops.name ||'未命名',
			show : ( ops.show &&  ops.show!='1')?false : true,    
			bizType:ops.code||'',
			preferLeaves:(ops && ops.preferLeaves && ops.preferLeaves=='1')?true:false,
			imageBasedLightingFactor :Cesium.Cartesian2(1.0, 1.0),
			loadSiblings:true,
			skipLevels:ops.skipLevels ? ops.skipLevels*1: 1,
			baseScreenSpaceError:ops.baseScreenSpaceError ? ops.baseScreenSpaceError*1: 1024,
			skipScreenSpaceErrorFactor:ops.skipScreenSpaceErrorFactor ? ops.skipScreenSpaceErrorFactor*1: 16,
			maximumMemoryUsage:ops.maximumMemoryUsage ? ops.maximumMemoryUsage*1: 512,
			maximumScreenSpaceError : ops.maximumScreenSpaceError ? ops.maximumScreenSpaceError*1: 16,
			skipLevelOfDetail : ops.skipLevelOfDetail ? (ops.skipLevelOfDetail=='on'?true:false): false,
			maximumNumberOfLoadedTiles : ops.maximumNumberOfLoadedTiles ? ops.maximumNumberOfLoadedTiles*1: 1024, //最大加载瓦片个数			
		}));
		
		primitive.readyPromise.then(function(tileset) {

			if(ops.posX && ops.posY && ops.posZ){
				  tileset._root.transform = VFG.Util.getPrimitiveModelMatrix(ops);
			}else{
	            var heightOffset =ops.z || 0;  //高度
	            var boundingSphere = tileset.boundingSphere; 
	            var cartographic = Cesium.Cartographic.fromCartesian(boundingSphere.center);
	            var surface = Cesium.Cartesian3.fromRadians(cartographic.longitude, cartographic.latitude, 0.0);
	            var offset = Cesium.Cartesian3.fromRadians(cartographic.longitude, cartographic.latitude, heightOffset);
	            var translation = Cesium.Cartesian3.subtract(offset, surface, new Cesium.Cartesian3());
	            tileset.modelMatrix = Cesium.Matrix4.fromTranslation(translation);
			}
			
		    if(ops.callBack){
		    	var result=VFG.Util.getCenterForModel(tileset,tileset._root.transform);
		    	ops.callBack(result);
		    }
		}).otherwise(function(error){
			console.log(error);
	    });
		this.Primitives.set(ops.id,primitive);
		this.Resource.set(ops.id,ops);
		return primitive;
	}else{
		return this.Primitives.get(ops.id);
	}
}

/**
 * id查询点
 */
VFG.Model.getById=function(id){
	if(this.Primitives.has(id)){
		return this.Primitives.get(id);
	}
}

VFG.Model.getResourceById=function(id){
	if(this.getResourceById.has(id)){
		return this.getResourceById.get(id);
	}
}

/**
 * 显示隐藏
 */
VFG.Model.showOrHideById=function(id,state){
	if(this.Primitives.has(id)){
		this.Primitives.get(id).show=state;
	}
}

VFG.Model.removeById=function(id){
	if(this.Primitives.has(id)){
		if(this.Layers.remove(this.Primitives.get(id))){
			this.Primitives.delete(id);
			this.Resource.delete(id);
		}
	}
}

;
///<jscompress sourcefile="ModelVideo.js" />
/**
 * viewer
 * option：{
 * 	videoUrl:视频地址
 *  modelUrl:模型地址
 *  modelScale:模型缩放
 * }
 */
ModelVideo = function(viewer,option) {
	this.option = Cesium.defaultValue(option, Cesium.defaultValue.EMPTY_OBJECT);
	this.viewer = Cesium.defaultValue(viewer, undefined);
	if (!viewer) {
		console.log('viewer参数必填!');
	}
	if (!option) {
		console.log('参数必填!');
	}
	this.primitive;
	this.videoEle;
	this.position=this.option.position;
	this.rotation=this.option.rotation;
	this.videoUrl=this.option.videoUrl;
	this.modelUrl=this.option.modelUrl;
	this.modelScale=this.option.modelScale||20;
	var _this=this;
	  
	_this.modelObject = [];
	_this.mtlArray = [];
	_this.objArray = [];
	_this.TextureArray = [];
	_this.index = 0;
	
	this.videoEle=this.createVideoEle(_this.videoUrl); 

    if (_this.videoEle) {
    	_this.videoEle.addEventListener("canplaythrough", function () {
    		_this.viewer.clock.onTick.addEventListener(_this.activeVideoListener,_this)
    	});
    }
	 _this.init();

}

ModelVideo.prototype.init = function () {
	var  _this=this;
	var request = new XMLHttpRequest();
    request.onreadystatechange = function() {
        if (request.readyState === 4 && request.status !== 404) {
        	
            //先初始化状态锁，不知道在这行不行
        	_this.mtlArray[_this.index]=false;
        	_this.objArray[_this.index]=false;
        	_this.modelObject[_this.index]=new OBJDoc(_this.modelUrl);
            var result = OBJDocparser.bind(_this.modelObject[_this.index])(request.responseText, _this.modelObject, _this.mtlArray, _this.objArray, _this.modelScale, false, _this.index); 
            if (!result) {
                g_objDoc = null; g_drawingInfo = null;
                return;
            }        
            
            //除了第一个参数，其他参数不变，这是为了异步操作的方便
			var data  =_this.modelObject[0];
			var drawingInfo  =data.getDrawingInfo();
			
		    var material = Cesium.Material.fromType('Image');
		    material.uniforms.image = _this.videoEle;
			
		    
		   // var material = Cesium.Material.fromType('Image');
		   // material.uniforms.image = _this.videoEle;
		    
		    
	        //旋转
			var mx = Cesium.Matrix3.fromRotationX(Cesium.Math.toRadians(_this.rotation.x));
			var my = Cesium.Matrix3.fromRotationY(Cesium.Math.toRadians(_this.rotation.y));
			var mz = Cesium.Matrix3.fromRotationZ(Cesium.Math.toRadians(_this.rotation.z));
			var rotationX = Cesium.Matrix4.fromRotationTranslation(mx);
			var rotationY = Cesium.Matrix4.fromRotationTranslation(my);
			var rotationZ = Cesium.Matrix4.fromRotationTranslation(mz);
	        
	        //平移
			var position = Cesium.Cartesian3.fromDegrees(_this.position.x,_this.position.y,_this.position.z);
			var m = Cesium.Transforms.eastNorthUpToFixedFrame(position);
			//var scale = _this.option.modelScale?_this.option.modelScale*1:Cesium.Matrix4.fromUniformScale(1);
	        // //缩放
	       // Cesium.Matrix4.multiply(m, scale, m);
	        //旋转、平移矩阵相乘
	        Cesium.Matrix4.multiply(m, rotationX, m);
	        Cesium.Matrix4.multiply(m, rotationY, m);
	        Cesium.Matrix4.multiply(m, rotationZ, m);
		    
		    
		    
         //  var position = Cesium.Cartesian3.fromDegrees(_this.position.x,_this.position.y,_this.position.z);
           var modelMatrix =m;// Cesium.Transforms.eastNorthUpToFixedFrame(position);
         
           var positions=drawingInfo.vertices;
           // 2 定义法向数组
           var normals = drawingInfo.normals;
           // 3 定义纹理数组
           var sts=drawingInfo.colors;
           var indices = drawingInfo.indices;
           // 5 创建Primitive
           _this.primitive = _this.viewer.scene.primitives.add(new Cesium.Primitive({
               geometryInstances: new Cesium.GeometryInstance({
                   geometry: new Cesium.Geometry({
                       attributes: {
                           position: new Cesium.GeometryAttribute({
                               componentDatatype: Cesium.ComponentDatatype.DOUBLE,
                               componentsPerAttribute: 3,
                               values: positions
                           }),
                           normal: new Cesium.GeometryAttribute({
                               componentDatatype: Cesium.ComponentDatatype.FLOAT,
                               componentsPerAttribute: 3,
                               values: normals
                           }),
                           st: new Cesium.GeometryAttribute({
                               componentDatatype: Cesium.ComponentDatatype.FLOAT,
                               componentsPerAttribute: 2,
                               values: sts
                           }),
                       },
                       indices: indices,
                       primitiveType: Cesium.PrimitiveType.TRIANGLES,
                       boundingSphere: Cesium.BoundingSphere.fromVertices(positions)
                   }),
               }),
              appearance: new Cesium.MaterialAppearance({
                   material:material,
                   faceForward : true, // 当绘制的三角面片法向不能朝向视点时，自动翻转法向，从而避免法向计算后发黑等问题
                   closed: false // 是否为封闭体，实际上执行的是是否进行背面裁剪
               }),
               modelMatrix: modelMatrix,
               asynchronous: false
           }));
        }
    };
    request.open('GET', this.modelUrl, true); 
    request.send();
}

ModelVideo.prototype.activeVideoListener = function (e) {
	var _this=this;
    try {
        if (_this._videoPlay && _this.videoEle.paused) _this.videoEle.play();
    } catch (e) {}
}
ModelVideo.prototype.deActiveVideo = function (e) {
	this.viewer.clock.onTick.removeEventListener(this.activeVideoListener, this);
}

ModelVideo.prototype.createVideoEle = function (e) {
    if(e){
    	this.videoId = "visualDomId";
        var t = document.createElement("SOURCE");
        t.type = "video/mp4",
        t.src = e;
        var i = document.createElement("SOURCE");
        i.type = "video/quicktime",
        i.src = e;
        var r = document.createElement("video");
        return r.setAttribute("autoplay", ''),
        r.setAttribute("loop", ''),
        r.setAttribute("crossorigin",''),
        r.setAttribute("controls",''),
        r.setAttribute("muted",''),
        r.setAttribute("id", this.videoId),
        r.appendChild(t),
        r.appendChild(i),
        r.style.display = "none", 
        document.body.appendChild(r),
        r
    }
}

ModelVideo.prototype.destroy = function () {
	  this.deActiveVideo();
      this.videoEle && this.videoEle.parentNode.removeChild(this.videoEle),
	  delete this.videoEle,
	  delete this.options,
	  delete this.viewer;
	  return Cesium.destroyObject(this);
	};
;
///<jscompress sourcefile="VFGPoint.js" />
/**
 * 坐标点操作
 */
VFG.Point=function(){
}
VFG.Point.Layers=new Cesium.CustomDataSource("pointsLayer");
VFG.Point.Render=new Map();

VFG.Point.LabelCollection=new Cesium.LabelCollection();
VFG.Point.PointPrimitiveCollection=new Cesium.PointPrimitiveCollection();
VFG.Point.BillboardCollection=new Cesium.BillboardCollection();
VFG.Point.Primitives=new Map();
VFG.Point.LabelMap=new Map();
VFG.Point.PointMap=new Map();
VFG.Point.BillboardMap=new Map();
/**
 * id查询点
 */
VFG.Point.getPointById=function(id){
	return this.Layers.entities.getById(id);
}

/**
 * 移出点
 */
VFG.Point.removePointById=function(id){
	this.Layers.entities.removeById(id);
}


/**
 * 添加点
 */
VFG.Point.addPoint=function(params,styleData){
	var entity=this.getPointById(params.id);
	if(entity){
		return entity;
	}
	var ops;
	if(styleData){
		styleData.id=params.id || `${params.lon}点`;
		styleData.name=params.name || '点';
		styleData.show=true;
		styleData.type=params.type ||'point',
		styleData.position=params.position;
		styleData.bizType=params.code||'';
		if(styleData.label){
			//styleData.label.text=params.name;
			styleData.label.text=(params.name.replace(/[^\x00-\xff]/g,"$&\x01").replace(/.{18}\x01?/g,"$&\n").replace(/\x01/g,"")) || '点';
		}
		ops=styleData;
	}else{
		ops={
		        id: params.id || `${params.lon}点`,
		        name:params.name || '点',
		        type:params.type ||'point',
		        show:true,
		        bizType:params.code||'',
		        position:params.position,
		        point:new Cesium.PointGraphics ( {
		            show : true,
		            pixelSize : params.pixelSize || 5,
		            heightReference : params.pixelSize || Cesium.HeightReference.NONE,
		            color : params.color || new Cesium.Color ( 255 , 255 , 0 , 1 ),
		            outlineColor : params.color || Cesium.Color.YELLOW,
		            outlineWidth : params.outlineWidth || 2,
		            scaleByDistance : params.scaleByDistance || new Cesium.NearFarScalar ( 0 , 1 , 5e10 , 1 ),
		            translucencyByDistance : params.translucencyByDistance || new Cesium.NearFarScalar ( 0 , 1 , 5e10 , 1 ),
		            distanceDisplayCondition : params.translucencyByDistance || new Cesium.DistanceDisplayCondition(0, 4.8e10),
		        } )
		    }
	}
	return this.Layers.entities.add(new Cesium.Entity(ops));
}

/**
 * 接口添加点
 */
VFG.Point.addPointFromAPI=function(viewer,pointRender,ctx){
	var _this=this;
	if(!pointRender){
		return;
	}
	var point=pointRender.point;
	var styles=pointRender.styles;
	
	if(!point){
		return;
	}
	var pointStyle;
	if(point!=null && styles.length>0){
		pointStyle=this.packagePoint(styles[0],ctx);
	}
	var entity=this.getPointById(point.id);
	if(entity){
		return entity;
	}
	//var position=Cesium.Cartesian3.fromDegrees(point.x*1,point.y*1,point.z*1+1340);
	VFG.Util.getSurfaceHeight(viewer, Cesium.Cartesian3.fromDegrees(point.x*1,point.y*1,0), {
		asyn:true,
		calback:function(heightTerrain, carto){
			var position=Cesium.Cartesian3.fromDegrees(point.x*1,point.y*1,heightTerrain+2);
			_this.addPoint({
				id:point.id,
				position:position,
				name:point.name,
			 },pointStyle);
		}
	});
	

}

/**
 * 批量添加接口点
 */
VFG.Point.batchAddPointFromAPI=function(viewer,points,ctx){
	var _this=this;
	var arr=[];
    if(points!=null && points.length>0){
    	for(var i=0;i<points.length;i++){
    		_this.addPointFromAPI(viewer,points[i],ctx)
    		arr.push(viewer,points[i].point.id);
    	}
    }
    return arr;
}

/**
 * 数据库表组装实体
 */
VFG.Point.packagePoint= function(ops,baseUrl) {
	if(!ops){
		return null;
	}
	var param={};
	if(ops.showForLabel=='1'){
		var eyeOffset=VFG.Util.getCartesian3(ops.eyeOffsetXForLabel,ops.eyeOffsetYForLabel,ops.eyeOffsetZForLabel);
		var pixelOffset=VFG.Util.getCartesian2(ops.pixelOffsetXForLabel*1,ops.pixelOffsetYForLabel);
		var backgroundPadding=VFG.Util.getCartesian2(ops.backgroundPaddingXForLabel,ops.backgroundPaddingYForLabel);
		var pixelOffsetScaleByDistance= VFG.Util.getNearFarScalar(ops.pixelOffsetScaleNearForLabel,ops.pixelOffsetScaleNearValueForLabel, ops.pixelOffsetScaleFarForLabel,ops.pixelOffsetScaleFarValueForLabel);
	    var scaleByDistance=VFG.Util.getNearFarScalar(ops.scalarNearForLabel,ops.scalarNearValueForLabel, ops.scalarFarForLabel,ops.scalarFarValueForLabel); 
	    var translucencyByDistance =VFG.Util.getNearFarScalar(ops.translucencyNearForLabel,ops.translucencyNearValueForLabel, ops.translucencyFarForLabel,ops.translucencyFarValueForLabel); 
	    var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(ops.displayNearForLabel,ops.displayFarForLabel);
	    param.label={
	        font: ops.fontForLabel?ops.fontForLabel:'',
	        //eyeOffset :eyeOffset?eyeOffset:Cesium.Cartesian3.ZERO ,
	        horizontalOrigin : VFG.Util.getHorizontalOrigin(ops.horizontalOriginForLabel) ,
	        verticalOrigin : VFG.Util.getVerticalOrigin(ops.verticalOriginForLabel) ,
	        scale: ops.scaleForLabel?ops.scaleForLabel:1,
	        fillColor :ops.fillColorForLabel?Cesium.Color.fromCssColorString(ops.fillColorForLabel):Cesium.Color.WHITE,
	        outlineWidth : ops.outlineWidthForLabel?ops.outlineWidthForLabel:0,
	        outlineColor:  ops.outlineColorForLabel?Cesium.Color.fromCssColorString(ops.outlineColorForLabel):Cesium.Color.WHITE,
	        pixelOffset: pixelOffset?pixelOffset:new Cesium.Cartesian2(0, 0),
	        showBackground: ops.showBackgroundForLabel&& ops.showBackgroundForLabel==1 ? true:false,
	        backgroundColor: ops.backgroundColorForLabel?Cesium.Color.fromCssColorString(ops.backgroundColorForLabel):new Cesium.Color(0.165, 0.165, 0.165, 0.8),
	        backgroundPadding : backgroundPadding?backgroundPadding:new Cesium.Cartesian2(0, 0),
	        pixelOffsetScaleByDistance :pixelOffsetScaleByDistance?pixelOffsetScaleByDistance:undefined,//偏移量比例
	        scaleByDistance:scaleByDistance?scaleByDistance:undefined, //缩放比例
	        translucencyByDistance:translucencyByDistance?translucencyByDistance:undefined,//半透明度比例            		
	        distanceDisplayCondition :distanceDisplayCondition?distanceDisplayCondition:undefined,
	        style :Cesium.LabelStyle.FILL_AND_OUTLINE,
	       // disableDepthTestDistance: Number.POSITIVE_INFINITY
	    }
	}
	if(ops.showForPoint=='1'){
	    var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(ops.displayNearForPoint,ops.displayFarForPoint);
	    var scaleByDistance= VFG.Util.getNearFarScalar(ops.scalarNearForPoint,ops.scalarNearValueForPoint, ops.scalarFarForPoint,ops.scalarFarValueForPoint); 
	    var translucencyByDistance= VFG.Util.getNearFarScalar(ops.translucencyNearForPoint,ops.translucencyNearValueForPoint, ops.translucencyFarForPoint,ops.translucencyFarValueForPoint); 
	    param.point={
			pixelSize : ops.pixelSizeForPoint||5,
			//heightReference:point.heightReference?point.heightReference: Cesium.HeightReference.NONE,
			color :ops.colorForPoint?Cesium.Color.fromCssColorString(ops.colorForPoint):Cesium.Color.WHITE,
			outlineColor: ops.outlineColorForPoint? Cesium.Color.fromCssColorString(ops.outlineColorForPoint):Cesium.Color.BLACK,
		    outlineWidth:ops.outlineWidthForPoint?ops.outlineWidthForPoint:0,
	        distanceDisplayCondition : distanceDisplayCondition?distanceDisplayCondition:undefined,
	        scaleByDistance:scaleByDistance?scaleByDistance:undefined, 
	        translucencyByDistance:translucencyByDistance?translucencyByDistance:undefined, 	
	       // disableDepthTestDistance: Number.POSITIVE_INFINITY
		}
	}
	if(ops.showForBillboard=='1'){
		var pixelOffset=VFG.Util.getCartesian2(ops.pixelOffsetXForBillboard*1,ops.pixelOffsetXForBillboard*1);
		var pixelOffsetScaleByDistance= VFG.Util.getNearFarScalar(ops.pixelOffsetScaleNearForBillboard,ops.pixelOffsetScaleNearValueForBillboard, ops.pixelOffsetScaleFarForBillboard,ops.pixelOffsetScaleFarValueForBillboard);
        var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(ops.displayNearForBillboard,ops.displayFarForBillboard);
        var scaleByDistance= VFG.Util.getNearFarScalar(ops.scalarNearForBillboard,ops.scalarNearValueForBillboard, ops.scalarFarForBillboard,ops.scalarFarValueForBillboard); 
        var translucencyByDistance =VFG.Util.getNearFarScalar(ops.translucencyNearForBillboard,ops.translucencyNearValueForBillboard, ops.translucencyFarForBillboard,ops.translucencyFarValueForBillboard); 
        param.billboard={
            image:baseUrl+ops.imageForBillboard,
            width: ops.widthForBillboard,
            height: ops.heightForBillboard,
            scale:ops.scaleForBillboard,
            sizeInMeters: false,
	        pixelOffset: pixelOffset?pixelOffset:new Cesium.Cartesian2(0, ops.heightForBillboard),
            eyeOffset:new Cesium.Cartesian3(0.0, 0, 0.0),
            horizontalOrigin : Cesium.HorizontalOrigin.CENTER,
            verticalOrigin :Cesium.VerticalOrigin.BOTTOM,
	        pixelOffsetScaleByDistance :pixelOffsetScaleByDistance?pixelOffsetScaleByDistance:undefined,//偏移量比例
            distanceDisplayCondition :distanceDisplayCondition?distanceDisplayCondition:undefined,
            scaleByDistance:scaleByDistance?scaleByDistance:undefined, //设置距离方位内
            translucencyByDistance:translucencyByDistance?translucencyByDistance:undefined,
           // disableDepthTestDistance: Number.POSITIVE_INFINITY
    	}
	}
	return param;
}

/**
 * 点飞行
 */
VFG.Point.flyToPoint=function(viewer,ctx,id){
    var res = common_ajax.ajaxFunc(ctx+"/biz/marker/point/getById",{id:id}, "json", null);
    if (undefined!=res && 200==res.code) {
    	var data=res.data;
    	if(data.cameraX && data.cameraY && data.cameraZ){
    		viewer.camera.flyTo({
    		    destination : new Cesium.Cartesian3(data.cameraX*1,data.cameraY*1, data.cameraZ*1),
    		    orientation : {
    		        heading : data.heading*1,
    		        pitch : data.pitch*1,
    		        roll : data.roll*1
    		    }
    		});
    	}else{
    		viewer.camera.flyTo({
    		    destination : Cesium.Cartesian3.fromDegrees(data.x*1, data.y*1, data.z*1+100)
    		});
    	}
    }else{
    	if(undefined!=res) layer.msg(res.message); else layer.msg("未知错误！！！");
    }
}

/**
 * 获取字符串的真实长度
 */
VFG.Point.getLabelLength=function(str) { 
    let len = str.length,
        trueLen = 0;
    for (let x = 0; x < len; x++) {
        if (str.charCodeAt(x) > 128) {
            trueLen += 2;
        } else {
            trueLen += 1;
        }
    }
    return trueLen;
}

/**
 * 获取label矩形区域被
 * position:{
 * 	x:经度
 * 	y:维度
 * 	z:高度
 * }
 * padding:{
 * 	top:顶部
 * 	bottom:底部
 * 	right:右侧
 * 	left:左侧
 * }
 */
VFG.Point.getLabelRectangle=function(viewer,position,padding) {
	var cartesian3=Cesium.Cartesian3.fromDegrees(position.x*1, position.x*1, position.x*z) ;
	var cartesian2=Cesium.SceneTransforms.wgs84ToWindowCoordinates(viewer.scene, cartesian3);
	var minX=cartesian2.x-padding.left;
	var minY=cartesian2.y-padding.bottom;
	var maxX=cartesian2.x+padding.right;
	var maxY=cartesian2.y+padding.top;
	return {
		minX:minX,
		minY:minY,
		maxX:maxX,
		maxY:maxY,
	}
}

VFG.Point.getLabelRectangleForC3=function(viewer,cartesian3,padding) {
	var cartesian2=Cesium.SceneTransforms.wgs84ToWindowCoordinates(viewer.scene, cartesian3);
	if(Cesium.defined(cartesian2)){
		var minX=cartesian2.x-padding.left;
		var minY=cartesian2.y-padding.bottom;
		var maxX=cartesian2.x+padding.right;
		var maxY=cartesian2.y+padding.top;
		return {
			minX:minX,
			minY:minY,
			maxX:maxX,
			maxY:maxY,
		}
	}else{
		return null;
	}
}


VFG.Point.getPointRectangleForC3=function(viewer,id,name,fontSize,cartesian3,padding) {
	var cartesian2=Cesium.SceneTransforms.wgs84ToWindowCoordinates(viewer.scene, cartesian3);
	if(Cesium.defined(cartesian2)){
		var L=this.getLabelLength(name)*fontSize;
		var minX=cartesian2.x-padding.left;
		var minY=cartesian2.y-padding.bottom;
		var maxX=cartesian2.x+padding.right+L;
		var maxY=cartesian2.y+padding.top;
	    var clientWidth=viewer.scene.canvas.clientWidth / 2;
	    var clientHeight=viewer.scene.canvas.clientHeight / 2;
	    var dx = Math.abs(clientWidth - cartesian2.x);
        var dy = Math.abs(clientHeight - cartesian2.y);
        var distance = Math.sqrt(Math.pow(dx,2)+Math.pow(dy,2));
		return {
			id:id,
			minX:minX,
			minY:minY,
			maxX:maxX,
			maxY:maxY,
			x:cartesian2.x,
			y:cartesian2.y,
			distance:distance
		}
	}else{
		return null;
	}
}

VFG.Point.isAnchorMeet=function(react,targetReact) {
    if ((react.minX < targetReact.maxX) && (targetReact.minX < react.maxX) &&
        (react.minY < targetReact.maxY) && (targetReact.minY < react.maxY)) {
        return true;
    }
    return false;
    
/*    if (react.minX >= targetReact.minX && react.minX >= targetReact.maxX) {
		return false;
	} else if (react.minX <= targetReact.minX && react.maxX <= targetReact.minX) {
		return false;
	} else if (react.minY >= targetReact.minY && react.minY >= targetReact.maxY) {
		return false;
	} else if (react.minY <= targetReact.minY && react.maxY <= targetReact.minY) {
		return false;
	}else{
		return true;
	}*/
}

VFG.Point.addWebsocket=function(viewer,data,ctx){
	var _this=this;
	var object=data.object;
	var event=data;
	var style=data.style;
	
	if(!data.show){
		var entity=_this.getPointById(event.id);
		if(entity){
			_this.removePointById(event.id);
		}
		return;
	}
	
	var pointStyle;
	if(style){
		pointStyle=this.packagePoint(style,ctx);
	}
	var entity=this.getPointById(event.id);
	var positon;
	if(entity){
		_this.removePointById(event.id);
		positon=entity.position.getValue();
	}
	
	if(positon){
		var entity=_this.addPoint({
			id:event.id,
			position:position,
			name:event.name,
			code:event.code
		 },pointStyle);
	}else{
		VFG.Util.getSurfaceHeight(viewer, Cesium.Cartesian3.fromDegrees(object.x*1,object.y*1,0), {
			asyn:true,
			calback:function(heightTerrain, carto){
				var position=Cesium.Cartesian3.fromDegrees(object.x*1,object.y*1,heightTerrain+2);
				var entity=_this.addPoint({
					id:event.id,
					position:position,
					name:event.name,
					code:event.code
				 },pointStyle);
			}
		});
	}
}


VFG.Point.addEntity=function(viewer,data,ctx){
	var _this=this;
	var point=data.point;
	var style=data.style;
	
	var pointStyle;
	if(style){
		pointStyle=this.packagePoint(style,ctx);
	}
	var entity=this.getPointById(point.id);
	if(entity){
		return entity;
	}
	var entity=_this.addPoint({
		id:point.id,
		position:Cesium.Cartesian3.fromDegrees(point.x*1,point.y*1,point.z*1),
		name:point.name,
		code:point.code
	 },pointStyle);
	return entity;
}

VFG.Point.addPrimitive=function(viewer,item,ctx){
	 var point=item.point;
	 var style=item.style;
	 if(!VFG.Point.Primitives.has(point.id)){
		 VFG.Point.Primitives.set(point.id,point)
		 var position=Cesium.Cartesian3.fromDegrees(point.x*1,point.y*1,point.z*1);
		 if(style){
			 if(style.showForLabel=='1'){
				var eyeOffset=VFG.Util.getCartesian3(style.eyeOffsetXForLabel,style.eyeOffsetYForLabel,style.eyeOffsetZForLabel);
				var pixelOffset=VFG.Util.getCartesian2(style.pixelOffsetXForLabel*1,style.pixelOffsetYForLabel);
				var backgroundPadding=VFG.Util.getCartesian2(style.backgroundPaddingXForLabel,style.backgroundPaddingYForLabel);
				var pixelOffsetScaleByDistance= VFG.Util.getNearFarScalar(style.pixelOffsetScaleNearForLabel,style.pixelOffsetScaleNearValueForLabel, style.pixelOffsetScaleFarForLabel,style.pixelOffsetScaleFarValueForLabel);
			    var scaleByDistance=VFG.Util.getNearFarScalar(style.scalarNearForLabel,style.scalarNearValueForLabel, style.scalarFarForLabel,style.scalarFarValueForLabel); 
			    var translucencyByDistance =VFG.Util.getNearFarScalar(style.translucencyNearForLabel,style.translucencyNearValueForLabel, style.translucencyFarForLabel,style.translucencyFarValueForLabel); 
			    var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(style.displayNearForLabel,style.displayFarForLabel);
			    var p=VFG.Point.LabelCollection.add({
			    	id: point.id,
			    	text:(point.name.replace(/\s*/g,"").replace(/[^\x00-\xff]/g,"$&\x01").replace(/.{18}\x01?/g,"$&\n").replace(/\x01/g,"")) || '点',
			    	position:position,
			        font: style.fontForLabel?style.fontForLabel:'',
			        //eyeOffset :eyeOffset?eyeOffset:Cesium.Cartesian3.ZERO ,
			        horizontalOrigin : VFG.Util.getHorizontalOrigin(style.horizontalOriginForLabel) ,
			        verticalOrigin : VFG.Util.getVerticalOrigin(style.verticalOriginForLabel) ,
			        scale: style.scaleForLabel?style.scaleForLabel:1,
			        fillColor :style.fillColorForLabel?Cesium.Color.fromCssColorString(style.fillColorForLabel):Cesium.Color.WHITE,
			        outlineWidth : style.outlineWidthForLabel?style.outlineWidthForLabel:0,
			        outlineColor:  style.outlineColorForLabel?Cesium.Color.fromCssColorString(style.outlineColorForLabel):Cesium.Color.WHITE,
			        pixelOffset: pixelOffset?pixelOffset:new Cesium.Cartesian2(0, 0),
			        showBackground: style.showBackgroundForLabel&& style.showBackgroundForLabel==1 ? true:false,
			        backgroundColor: style.backgroundColorForLabel?Cesium.Color.fromCssColorString(style.backgroundColorForLabel):new Cesium.Color(0.165, 0.165, 0.165, 0.8),
			        backgroundPadding : backgroundPadding?backgroundPadding:new Cesium.Cartesian2(0, 0),
			        pixelOffsetScaleByDistance :pixelOffsetScaleByDistance?pixelOffsetScaleByDistance:undefined,//偏移量比例
			        scaleByDistance:scaleByDistance?scaleByDistance:undefined, //缩放比例
			        translucencyByDistance:translucencyByDistance?translucencyByDistance:undefined,//半透明度比例            		
			        distanceDisplayCondition :distanceDisplayCondition?distanceDisplayCondition:undefined,
			        style :Cesium.LabelStyle.FILL_AND_OUTLINE,
			       // disableDepthTestDistance: Number.POSITIVE_INFINITY
			    });
			    VFG.Point.LabelMap.set(point.id,p);
			 }
			 if(style.showForBillboard=='1'){
				var pixelOffset=VFG.Util.getCartesian2(style.pixelOffsetXForBillboard*1,style.pixelOffsetXForBillboard*1);
				var pixelOffsetScaleByDistance= VFG.Util.getNearFarScalar(style.pixelOffsetScaleNearForBillboard,style.pixelOffsetScaleNearValueForBillboard, style.pixelOffsetScaleFarForBillboard,style.pixelOffsetScaleFarValueForBillboard);
		        var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(style.displayNearForBillboard,style.displayFarForBillboard);
		        var scaleByDistance= VFG.Util.getNearFarScalar(style.scalarNearForBillboard,style.scalarNearValueForBillboard, style.scalarFarForBillboard,style.scalarFarValueForBillboard); 
		        var translucencyByDistance =VFG.Util.getNearFarScalar(style.translucencyNearForBillboard,style.translucencyNearValueForBillboard, style.translucencyFarForBillboard,style.translucencyFarValueForBillboard); 
		        var p=VFG.Point.BillboardCollection.add({
		        	id: point.id,
		        	position: position,
		            image:ctx+style.imageForBillboard,
		            width: style.widthForBillboard,
		            height: style.heightForBillboard,
		            scale:style.scaleForBillboard,
		            sizeInMeters: false,
			        pixelOffset: pixelOffset?pixelOffset:new Cesium.Cartesian2(0, style.heightForBillboard),
		            eyeOffset:new Cesium.Cartesian3(0.0, 0, 0.0),
		            horizontalOrigin : Cesium.HorizontalOrigin.CENTER,
		            verticalOrigin :Cesium.VerticalOrigin.BOTTOM,
			        pixelOffsetScaleByDistance :pixelOffsetScaleByDistance?pixelOffsetScaleByDistance:undefined,//偏移量比例
		            distanceDisplayCondition :distanceDisplayCondition?distanceDisplayCondition:undefined,
		            scaleByDistance:scaleByDistance?scaleByDistance:undefined, //设置距离方位内
		            translucencyByDistance:translucencyByDistance?translucencyByDistance:undefined,
		    	});
		        VFG.Point.BillboardMap.set(point.id,p);
			 }
			 if(style.showForPoint=='1'){
			    var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(style.displayNearForPoint,style.displayFarForPoint);
			    var scaleByDistance= VFG.Util.getNearFarScalar(style.scalarNearForPoint,style.scalarNearValueForPoint, style.scalarFarForPoint,style.scalarFarValueForPoint); 
			    var translucencyByDistance= VFG.Util.getNearFarScalar(style.translucencyNearForPoint,style.translucencyNearValueForPoint, style.translucencyFarForPoint,style.translucencyFarValueForPoint); 
			    var p=VFG.Point.PointPrimitiveCollection.add({
			    	id: point.id,
			    	position: position,
					pixelSize : style.pixelSizeForPoint||5,
					//heightReference:point.heightReference?point.heightReference: Cesium.HeightReference.NONE,
					color :style.colorForPoint?Cesium.Color.fromCssColorString(style.colorForPoint):Cesium.Color.WHITE,
					outlineColor: style.outlineColorForPoint? Cesium.Color.fromCssColorString(style.outlineColorForPoint):Cesium.Color.BLACK,
				    outlineWidth:style.outlineWidthForPoint?style.outlineWidthForPoint:0,
			        distanceDisplayCondition : distanceDisplayCondition?distanceDisplayCondition:undefined,
			        scaleByDistance:scaleByDistance?scaleByDistance:undefined, 
			        translucencyByDistance:translucencyByDistance?translucencyByDistance:undefined, 	
			        //disableDepthTestDistance: Number.POSITIVE_INFINITY
				});
			    VFG.Point.PointMap.set(point.id,p);
			 }
		 }else{
			var position=Cesium.Cartesian3.fromDegrees(point.x*1,point.y*1,point.z*1);
			 var p=VFG.Point.PointPrimitiveCollection.add({
				  id: point.id,
		          pixelSize: 5,
		          color: Cesium.Color.RED,
		          color :new Cesium.Color ( 255 , 255 , 0 , 1 ),
		          outlineColor : Cesium.Color.YELLOW,
		          outlineWidth :2,
		          position: position
		     });
			 VFG.Point.PointMap.set(point.id,p);
		 }
	 }
}

/**
 * 获取实体
 */
VFG.Point.getPrimitiveById=function(id){
	return VFG.Point.Primitives.get(id);
}

/**
 * 移出点
 */
VFG.Point.removePrimitiveById=function(id){
	if(VFG.Point.LabelMap.has(id)){
		VFG.Point.LabelCollection.remove(VFG.Point.LabelMap.get(id));
		VFG.Point.LabelMap.delete(id);
	}
	if(VFG.Point.PointMap.has(id)){
		VFG.Point.PointPrimitiveCollection.remove(VFG.Point.PointMap.get(id));
		VFG.Point.PointMap.delete(id);
		
	}
	if(VFG.Point.BillboardMap.has(id)){
		VFG.Point.BillboardCollection.remove(VFG.Point.BillboardMap.get(id));
		VFG.Point.BillboardMap.delete(id)
	}
	VFG.Point.Primitives.delete(id)
}

/**
 * 显示隐藏
 */
VFG.Point.showOrHidePrimitiveById=function(id,state){
	if(VFG.Point.LabelMap.has(id)){
		VFG.Point.LabelMap.get(id).show=state;
	}
	if(VFG.Point.PointMap.has(id)){
		VFG.Point.PointMap.get(id).show=state;
	}
	if(VFG.Point.BillboardMap.has(id)){
		VFG.Point.BillboardMap.get(id).show=state;
	}
}
;
///<jscompress sourcefile="VFGPointAvoid.js" />
/**
 * 标签避让
 */
VFG.Point.Avoid=function(viewer,option){
	this.viewer=viewer;
	this.padding=option.padding|| {
		top:10,
		right:10,
		bottom:10,
		left:10,
	};
	this.fontSize=option.fontSize||14;
	this._layers=option.layers;
	this.init();
}
VFG.Point.Avoid.prototype.init = function () {
	var _this=this;
	this.avoid=function(){
		var entities=_this._layers.entities.values;
		var rectangles=[];
		for(var i=0;i<entities.length;i++){
			var entity=entities[i];
			var rec;
			if(entity.label){
				rec=_this.getPointRectangleForC3(entity);
				if(rec){
					rectangles.push(rec);
				}
			}
		}
		//排序
		rectangles.sort(function(a,b){
			return -(a.y - b.y); 
		});
		var showItems=[];
		var hideItems=[];
		_this.calculation(rectangles,showItems,hideItems);
		_this.show(showItems);
		_this.hide(hideItems);
	}
	this.viewer.scene.camera.moveEnd.addEventListener(this.avoid);
}
/**
 * 计算是否相交
 */
VFG.Point.Avoid.prototype.calculation=function(rectangles,showItems,hideItems){
	var _this=this;
	for(var i=0;i<rectangles.length;i++){
		var targRec=rectangles[i];
		if(i==0){
			showItems.push(targRec);
		}else{
			var show=true;
			for(var j=0;j<showItems.length;j++){
	            var curRec = showItems[j];
				var isAnchorMeet=_this.isAnchorMeet(curRec,targRec) ;
				show=!isAnchorMeet;
			}
			if(show){
				showItems.push(targRec);
			}else{
				hideItems.push(targRec);
			}
		}
	}
}

VFG.Point.Avoid.prototype.hide=function(hideItems){
	var _this=this;
	for(var i=0;i<hideItems.length;i++){
		_this._layers.entities.getById(hideItems[i].id).show=false;
	}
}
VFG.Point.Avoid.prototype.show=function(showItems){
	var _this=this;
	for(var i=0;i<showItems.length;i++){
		_this._layers.entities.getById(showItems[i].id).show=true;
	}
}

/**
 * 坐标计算屏幕矩形
 */
VFG.Point.Avoid.prototype.getPointRectangleForC3=function(entity) {
	var cartesian3=entity.position.getValue();
	if(Cesium.defined(cartesian3)){
		var cartesian2=Cesium.SceneTransforms.wgs84ToWindowCoordinates(this.viewer.scene,cartesian3);
		if(Cesium.defined(cartesian2)){
			var L=this.getLabelLength(entity.name)*this.fontSize;
			var minX=cartesian2.x-this.padding.left;
			var minY=cartesian2.y-this.padding.bottom;
			var maxX=cartesian2.x+this.padding.right+L;
			var maxY=cartesian2.y+this.padding.top;
		    var clientWidth=this.viewer.scene.canvas.clientWidth / 2;
		    var clientHeight=this.viewer.scene.canvas.clientHeight / 2;
		    var dx = Math.abs(clientWidth - cartesian2.x);
	        var dy = Math.abs(clientHeight - cartesian2.y);
	        var distance = Math.sqrt(Math.pow(dx,2)+Math.pow(dy,2));
			return {
				id:entity.id,
				minX:minX,
				minY:minY,
				maxX:maxX,
				maxY:maxY,
				x:cartesian2.x,
				y:cartesian2.y,
				distance:distance
			}
		}
	}
	return null;
}

/**
 * 判断碰撞
 */
VFG.Point.Avoid.prototype.isAnchorMeet=function(react,targetReact) {
    if ((react.minX < targetReact.maxX) && (targetReact.minX < react.maxX) &&
        (react.minY < targetReact.maxY) && (targetReact.minY < react.maxY)) {
        return true;
    }
    return false;
}

/**
 * 文字长度
 */
VFG.Point.Avoid.prototype.getLabelLength=function(str) { 
    let len = str.length,
        trueLen = 0;
    for (let x = 0; x < len; x++) {
        if (str.charCodeAt(x) > 128) {
            trueLen += 2;
        } else {
            trueLen += 1;
        }
    }
    return trueLen;
}

VFG.Point.Avoid.prototype.destroy = function () {
  this.viewer.scene.camera.moveEnd.removeEventListender(this.avoid) 
  return Cesium.destroyObject(this);
};;
///<jscompress sourcefile="VFGPointProvider.js" />
function VFGPointProvider(viewer,options) {
  options = Cesium.defaultValue(options, Cesium.defaultValue.EMPTY_OBJECT);
  this._tilingScheme = Cesium.defined(options.tilingScheme)
    ? options.tilingScheme
    : new Cesium.GeographicTilingScheme({ ellipsoid: options.ellipsoid });
  this._color = Cesium.defaultValue(options.color, Cesium.Color.YELLOW);
  this._errorEvent = new Cesium.Event();
  this._tileWidth = Cesium.defaultValue(options.tileWidth, 256);
  this._tileHeight = Cesium.defaultValue(options.tileHeight, 256);
  this._readyPromise = Cesium.when.resolve(true);
  this._cacheMap=new Map();
  this._viewer=viewer;
  this._url=options.url;
  this._sceneId=options.sceneId;
  this._ctx=options.ctx;
  this._level = options.level ||11;
  
  /**
	 * The default alpha blending value of this provider, with 0.0 representing
	 * fully transparent and 1.0 representing fully opaque.
	 * 
	 * @type {Number|undefined}
	 * @default undefined
	 */

  this.defaultAlpha = options.alpha;

  /**
	 * The default alpha blending value on the night side of the globe of this
	 * provider, with 0.0 representing fully transparent and 1.0 representing
	 * fully opaque.
	 * 
	 * @type {Number|undefined}
	 * @default undefined
	 */
  this.defaultNightAlpha = undefined;

  /**
	 * The default alpha blending value on the day side of the globe of this
	 * provider, with 0.0 representing fully transparent and 1.0 representing
	 * fully opaque.
	 * 
	 * @type {Number|undefined}
	 * @default undefined
	 */
  this.defaultDayAlpha = undefined;

  /**
	 * The default brightness of this provider. 1.0 uses the unmodified imagery
	 * color. Less than 1.0 makes the imagery darker while greater than 1.0
	 * makes it brighter.
	 * 
	 * @type {Number|undefined}
	 * @default undefined
	 */
  this.defaultBrightness = undefined;

  /**
	 * The default contrast of this provider. 1.0 uses the unmodified imagery
	 * color. Less than 1.0 reduces the contrast while greater than 1.0
	 * increases it.
	 * 
	 * @type {Number|undefined}
	 * @default undefined
	 */
  this.defaultContrast = undefined;

  /**
	 * The default hue of this provider in radians. 0.0 uses the unmodified
	 * imagery color.
	 * 
	 * @type {Number|undefined}
	 * @default undefined
	 */
  this.defaultHue = undefined;

  /**
	 * The default saturation of this provider. 1.0 uses the unmodified imagery
	 * color. Less than 1.0 reduces the saturation while greater than 1.0
	 * increases it.
	 * 
	 * @type {Number|undefined}
	 * @default undefined
	 */
  this.defaultSaturation = undefined;

  /**
	 * The default gamma correction to apply to this provider. 1.0 uses the
	 * unmodified imagery color.
	 * 
	 * @type {Number|undefined}
	 * @default undefined
	 */
  this.defaultGamma = undefined;

  /**
	 * The default texture minification filter to apply to this provider.
	 * 
	 * @type {TextureMinificationFilter}
	 * @default undefined
	 */
  this.defaultMinificationFilter = undefined;

  /**
	 * The default texture magnification filter to apply to this provider.
	 * 
	 * @type {TextureMagnificationFilter}
	 * @default undefined
	 */
  this.defaultMagnificationFilter = undefined;
}

Object.defineProperties(VFGPointProvider.prototype, {
  /**
	 * Gets the proxy used by this provider.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {Proxy}
	 * @readonly
	 */
  proxy: {
    get: function () {
      return undefined;
    },
  },

  /**
	 * Gets the width of each tile, in pixels. This function should not be
	 * called before {@link VFGPointProvider#ready} returns true.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {Number}
	 * @readonly
	 */
  tileWidth: {
    get: function () {
      return this._tileWidth;
    },
  },

  /**
	 * Gets the height of each tile, in pixels. This function should not be
	 * called before {@link VFGPointProvider#ready} returns true.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {Number}
	 * @readonly
	 */
  tileHeight: {
    get: function () {
      return this._tileHeight;
    },
  },

  /**
	 * Gets the maximum level-of-detail that can be requested. This function
	 * should not be called before {@link VFGPointProvider#ready} returns true.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {Number|undefined}
	 * @readonly
	 */
  maximumLevel: {
    get: function () {
      return undefined;
    },
  },

  /**
	 * Gets the minimum level-of-detail that can be requested. This function
	 * should not be called before {@link VFGPointProvider#ready} returns true.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {Number}
	 * @readonly
	 */
  minimumLevel: {
    get: function () {
      return undefined;
    },
  },

  /**
	 * Gets the tiling scheme used by this provider. This function should not be
	 * called before {@link VFGPointProvider#ready} returns true.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {TilingScheme}
	 * @readonly
	 */
  tilingScheme: {
    get: function () {
      return this._tilingScheme;
    },
  },

  /**
	 * Gets the rectangle, in radians, of the imagery provided by this instance.
	 * This function should not be called before {@link VFGPointProvider#ready}
	 * returns true.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {Rectangle}
	 * @readonly
	 */
  rectangle: {
    get: function () {
      return this._tilingScheme.rectangle;
    },
  },

  /**
	 * Gets the tile discard policy. If not undefined, the discard policy is
	 * responsible for filtering out "missing" tiles via its shouldDiscardImage
	 * function. If this function returns undefined, no tiles are filtered. This
	 * function should not be called before {@link VFGPointProvider#ready}
	 * returns true.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {TileDiscardPolicy}
	 * @readonly
	 */
  tileDiscardPolicy: {
    get: function () {
      return undefined;
    },
  },

  /**
	 * Gets an event that is raised when the imagery provider encounters an
	 * asynchronous error. By subscribing to the event, you will be notified of
	 * the error and can potentially recover from it. Event listeners are passed
	 * an instance of {@link TileProviderError}.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {Event}
	 * @readonly
	 */
  errorEvent: {
    get: function () {
      return this._errorEvent;
    },
  },

  /**
	 * Gets a value indicating whether or not the provider is ready for use.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {Boolean}
	 * @readonly
	 */
  ready: {
    get: function () {
      return true;
    },
  },

  /**
	 * Gets a promise that resolves to true when the provider is ready for use.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {Promise.<Boolean>}
	 * @readonly
	 */
  readyPromise: {
    get: function () {
      return this._readyPromise;
    },
  },

  /**
	 * Gets the credit to display when this imagery provider is active.
	 * Typically this is used to credit the source of the imagery. This function
	 * should not be called before {@link VFGPointProvider#ready} returns true.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {Credit}
	 * @readonly
	 */
  credit: {
    get: function () {
      return undefined;
    },
  },

  /**
	 * Gets a value indicating whether or not the images provided by this
	 * imagery provider include an alpha channel. If this property is false, an
	 * alpha channel, if present, will be ignored. If this property is true, any
	 * images without an alpha channel will be treated as if their alpha is 1.0
	 * everywhere. Setting this property to false reduces memory usage and
	 * texture upload time.
	 * 
	 * @memberof VFGPointProvider.prototype
	 * @type {Boolean}
	 * @readonly
	 */
  hasAlphaChannel: {
    get: function () {
      return true;
    },
  },
});

/**
 * Gets the credits to be displayed when a given tile is displayed.
 * 
 * @param {Number}
 *            x The tile X coordinate.
 * @param {Number}
 *            y The tile Y coordinate.
 * @param {Number}
 *            level The tile level;
 * @returns {Credit[]} The credits to be displayed when the tile is displayed.
 * 
 * @exception {DeveloperError}
 *                <code>getTileCredits</code> must not be called before the
 *                imagery provider is ready.
 */
VFGPointProvider.prototype.getTileCredits = function (
  x,
  y,
  level
) {
  return undefined;
};

/**
 * Requests the image for a given tile. This function should not be called
 * before {@link VFGPointProvider#ready} returns true.
 * 
 * @param {Number}
 *            x The tile X coordinate.
 * @param {Number}
 *            y The tile Y coordinate.
 * @param {Number}
 *            level The tile level.
 * @param {Request}
 *            [request] The request object. Intended for internal use only.
 * @returns {Promise.<HTMLImageElement|HTMLCanvasElement>|undefined} A promise
 *          for the image that will resolve when the image is available, or
 *          undefined if there are too many active requests to the server, and
 *          the request should be retried later. The resolved image may be
 *          either an Image or a Canvas DOM object.
 */
VFGPointProvider.prototype.requestImage = function (
  x,
  y,
  level,
  request
) {
	
	// 计算加载范围
	// 缓存加载范围
	// 判断是否超出范围
	// 不在移除
	try{
		 if(level>=this._level){
/*			  var key=this.getKey(x,y,level);
			  if(this._cacheMap.has(key)){
				  var ids=this._cacheMap.get(key);
				  if(ids){
					  for(var i=0;i<ids.length;i++){
							 if(ids[i]) VFG.Point.removePointById(ids[i]);
					  }
				  }
				  this._cacheMap.delete(key);
			  }
			 this._cacheMap.set(key,null);*/
			 this.loadPoint(x, y,level);
		 }		
	}catch (e) {
		console.log(e);
	}
	  var canvas = document.createElement("canvas");
	  canvas.width = 256;
	  canvas.height = 256;
	  var context = canvas.getContext('2d');
	  var cssColor = this._color.toCssColorString();
	  context.strokeStyle = cssColor;
	  context.lineWidth = 2;
	  context.strokeRect(1, 1, 255, 255);
	
	  var interval = 180.0 / Math.pow(2, level);
	  var lon = (x + 0.5) * interval-180;
	  var lat = 90 - (y + 0.5) * interval;
	  // var label = 'L-' + level + 'X-' + x + 'Y-' + y;
	  var labelLevel = '';
	  var labelLon = '';
	  var labelLat = '';
	  if (lon > 0) {
	     if (lat > 0) {
	         // label = 'L' + level + 'E' + lon + 'N' + lat;
	         labelLevel = 'L' + level;
	         labelLon = 'E' + lon;
	         labelLat = 'N' + lat;
	     } else {
	         // label = 'L' + level + 'E' + lon + 'S' + (-lat);
	         labelLevel = 'L' + level;
	         labelLon = 'E' + lon;
	         labelLat = 'N' + (-lat);
	     }
	  } else {
	     if (lat > 0) {
	         // label = 'L' + level + 'W' + (-lon) + 'N' + lat;
	         labelLevel = 'L' + level;
	         labelLon = 'E' + (-lon);
	         labelLat = 'N' + lat;
	     } else {
	         // label = 'L' + level + 'W' + (-lon) + 'S' + (-lat);
	         labelLevel = 'L' + level;
	         labelLon = 'E' + (-lon);
	         labelLat = 'N' + (-lat);
	     }
	  }
	  context.textAlign = 'center';
	  context.fillStyle = cssColor;
	  if (level > 10) {
	     context.font = 'bold 16px Arial';
	     context.fillText(labelLevel, 124, 100);
	     context.fillText(labelLon, 124, 124);
	     context.fillText(labelLat, 124, 148);
	  } else {
	     context.font = 'bold 25px Arial';
	     context.fillText(labelLevel, 124, 94);
	     context.fillText(labelLon, 124, 124);
	     context.fillText(labelLat, 124, 154);
	 }  
  return canvas;
};

/**
 * 唯一标识
 */
VFGPointProvider.prototype.getKey = function ( x,y,level) {
	return x+''+y+''+level;
};


VFGPointProvider.prototype.loadPoint = function (x, y, level) {
	var _this=this;
	var rec=this._tilingScheme.tileXYToNativeRectangle(x, y, level);
	if(rec){
		$.ajax({
			type : "post",
			url : _this._url,
			data : {
				xmin:rec.west,
				ymin:rec.south,
				xmax:rec.east,
				ymax:rec.north,
				level:level,
				sceneId:_this._sceneId,
				count:10,
			},
			dataType : "json",
			contentType: "application/x-www-form-urlencoded; charset=UTF-8",
			async: true,
			cache: false,
			success:function(res){
				if(undefined!=res && 200==res.code) {
					var points=res.data;
		            if(points!=null && points.length>0){
		            	 _this._cacheMap.set(_this.getKey(x,y,level),VFG.Point.batchAddPointFromAPI(_this._viewer,points,_this._ctx));
		            }else{
		            	 _this._cacheMap.delete(_this.getKey(x,y,level));
		            }
				}
			}
		});
	}
};

/**
 * 获取场景范围
 */
VFGPointProvider.prototype.getCurrentExtent=function() {
	var viewer=this._viewer;
    // 范围对象
    var extent = {};

    // 得到当前三维场景
    var scene = viewer.scene;

    // 得到当前三维场景的椭球体
    var ellipsoid = scene.globe.ellipsoid;
    var canvas = scene.canvas;

    // canvas左上角
    var car3_lt = viewer.camera.pickEllipsoid(new Cesium.Cartesian2(0, 0), ellipsoid);

    // canvas右下角
    var car3_rb = viewer.camera.pickEllipsoid(new Cesium.Cartesian2(canvas.width, canvas.height), ellipsoid);

    console.log(car3_lt,car3_rb);
    // 当canvas左上角和右下角全部在椭球体上
    if (car3_lt && car3_rb) {
        var carto_lt = ellipsoid.cartesianToCartographic(car3_lt);
        var carto_rb = ellipsoid.cartesianToCartographic(car3_rb);
        extent.xmin = Cesium.Math.toDegrees(carto_lt.longitude);
        extent.ymax = Cesium.Math.toDegrees(carto_lt.latitude);
        extent.xmax = Cesium.Math.toDegrees(carto_rb.longitude);
        extent.ymin = Cesium.Math.toDegrees(carto_rb.latitude);
    }

    // 当canvas左上角不在但右下角在椭球体上
    else if (!car3_lt && car3_rb) {
        var car3_lt2 = null;
        var yIndex = 0;
        do {
            // 这里每次10像素递加，一是10像素相差不大，二是为了提高程序运行效率
            yIndex <= canvas.height ? yIndex += 10 : canvas.height;
            car3_lt2 = viewer.camera.pickEllipsoid(new Cesium.Cartesian2(0, yIndex), ellipsoid);
        } while (!car3_lt2);
        var carto_lt2 = ellipsoid.cartesianToCartographic(car3_lt2);
        var carto_rb2 = ellipsoid.cartesianToCartographic(car3_rb);
        extent.xmin = Cesium.Math.toDegrees(carto_lt2.longitude);
        extent.ymax = Cesium.Math.toDegrees(carto_lt2.latitude);
        extent.xmax = Cesium.Math.toDegrees(carto_rb2.longitude);
        extent.ymin = Cesium.Math.toDegrees(carto_rb2.latitude);
    }
    // 获取高度
    extent.height = Math.ceil(viewer.camera.positionCartographic.height);
    return extent;
}



/**
 * Picking features is not currently supported by this imagery provider, so this
 * function simply returns undefined.
 * 
 * @param {Number}
 *            x The tile X coordinate.
 * @param {Number}
 *            y The tile Y coordinate.
 * @param {Number}
 *            level The tile level.
 * @param {Number}
 *            longitude The longitude at which to pick features.
 * @param {Number}
 *            latitude The latitude at which to pick features.
 * @return {Promise.<ImageryLayerFeatureInfo[]>|undefined} A promise for the
 *         picked features that will resolve when the asynchronous picking
 *         completes. The resolved value is an array of
 *         {@link ImageryLayerFeatureInfo} instances. The array may be empty if
 *         no features are found at the given location. It may also be undefined
 *         if picking is not supported.
 */
VFGPointProvider.prototype.pickFeatures = function (
  x,
  y,
  level,
  longitude,
  latitude
) {
  return undefined;
};
;
///<jscompress sourcefile="VFGPolygon.js" />
VFG.Polygon=function(){
}
VFG.Polygon.Layers=new Cesium.CustomDataSource("polygonsLayer");
VFG.Polygon.Primitives=new Map();
/**
 * id查询点
 */
VFG.Polygon.getEntityById=function(id){
	return this.Layers.entities.getById(id);
}

/**
 * 移出
 */
VFG.Polygon.removeEntityById=function(id){
	this.Layers.entities.removeById(id);
	this.Primitives.delete(id);
}

VFG.Polygon.getPrimitiveById=function(id){
	return this.Primitives.get(id);
}

VFG.Polygon.addEntity=function(param,polygon){
	var entity=this.getEntityById(param.id);
	if(entity){
		return entity;
	}
	return this.Layers.entities.add(new Cesium.Entity({
    	id:param.id,
    	name:param.name||'',
    	show: true,
    	bizType:param.code||'',
    	polygon: polygon
    }));
}

VFG.Polygon.addEntityForAPI=function(param){
	var polygon=this.packagePolygon(param);
	this.addEntity(param.polygon,polygon)
	if(!this.Primitives.has(param.polygon.id)){
		this.Primitives.set(param.polygon.id,param.polygon)
	}
}

VFG.Polygon.packagePolygon=function(param){
	var polygon=param.polygon;
	var style=param.style;
	var styleObj;
	if(style){
		styleObj=this.getPolygonForAPI(style);
		styleObj.hierarchy=this.getHierarchy(polygon.points);
		return styleObj;
	}else{
		return {
			hierarchy:this.getHierarchy(polygon.points),
            material: Cesium.Color.RED.withAlpha(0.5),
            outline: true,
            outlineColor: Cesium.Color.YELLOW.withAlpha(1)
        }
	}
}

VFG.Polygon.getHierarchy=function(points){
	if(points){
		var positions=JSON.parse(points);
		if(positions.length>=2){
			var Hierarchy=[];
			for(var i=0;i<positions.length;i++){
				Hierarchy.push(Cesium.Cartesian3.fromDegrees(positions[i].x*1,positions[i].y*1,positions[i].z*1));
			}
			return new Cesium.PolygonHierarchy(Hierarchy);
		}
	}else{
		return [];
	}
}

VFG.Polygon.getPolygonForAPI = function(data) {
	var _this=this;
	var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(data.distanceDisplayConditionX*1,data.distanceDisplayConditionY*1);
	var options={
		stRotation:data.stRotation?data.stRotation:0.0,
		fill:data.fill?data.fill:false,
		material:data.color? Cesium.Color.fromCssColorString(data.color):Cesium.Color.BLACK,
		outline:data.outline && data.outline=='1'  ?true:false,
		outlineColor:data.outlineColor? Cesium.Color.fromCssColorString(data.outlineColor):Cesium.Color.BLACK,
		outlineWidth:data.outlineWidth?data.outlineWidth*1:0.0,
		closeTop:data.closeTop?data.closeTop:false,
		closeBottom:data.closeBottom?data.closeBottom:false,
		arcType:Cesium.ArcType.GEODESIC,
		shadows:data.shadows?data.shadows:false,
		distanceDisplayCondition:distanceDisplayCondition||null,
		classificationType:VFG.Util.getClassificationType(data.classificationType)
	}
	options.perPositionHeight=(data.perPositionHeight && data.perPositionHeight=='1'  ?true:false);
	 if(data.height!=null){
		 options.height=data.height?data.height*1:0.0;
	 }
	 if(data.heightReference){
		 options.heightReference=VFG.Util.getHeightReference(data.heightReference);
	 }
	 if(data.extrudedHeight){
		 options.extrudedHeight=data.extrudedHeight?data.extrudedHeight*1:0.0;
	 }
	 if(data.extrudedHeightReference){
		 options.extrudedHeightReference=VFG.Util.getHeightReference(data.extrudedHeightReference);
	 }
	return options;
};

VFG.Polygon.showOrHideEntityById=function(id,state){
	var Entity=this.Layers.entities.getById(id);
	if(Entity){
		Entity.show=state;
	}
}


VFG.Polygon.addPrimitive=function(){
}

;
///<jscompress sourcefile="VFGPolyline.js" />
VFG.Polyline=function(){
}
VFG.Polyline.Layers=new Cesium.CustomDataSource("polylinesLayer");
VFG.Polyline.Primitives=new Map();
/**
 * id查询点
 */
VFG.Polyline.getEntityById=function(id){
	return this.Layers.entities.getById(id);
}

/**
 * 移出
 */
VFG.Polyline.removeEntityById=function(id){
	this.Layers.entities.removeById(id);
	this.Primitives.delete(id);
}

VFG.Polyline.getPrimitiveById=function(id){
	return this.Primitives.get(id);
}
VFG.Polyline.addEntity=function(param,polyline){
	var entity=this.getEntityById(param.id);
	if(entity){
		return entity;
	}
	return this.Layers.entities.add(new Cesium.Entity({
    	id:param.id,
    	name:param.name||'',
    	show: true,
    	bizType:param.code||'',
    	polyline: polyline
    }));
}

VFG.Polyline.addEntityForAPI=function(param){
	var polyline=this.packagePolyline(param);
	this.addEntity(param.polyline,polyline);
	if(!this.Primitives.has(param.polyline.id)){
		this.Primitives.set(param.polyline.id,param.polyline)
	}
}

VFG.Polyline.packagePolyline=function(param){
	var polyline=param.polyline;
	var style=param.style;
	var styleObj;
	if(style){
		styleObj=this.getPolylineForAPI(style);
		styleObj.positions=this.getPositions(polyline.points);
		return styleObj;
	}else{
		return {
            show: true,
            positions:this.getPositions(polyline.points),
            material:Cesium.Color.RED,
            width:2
        }
	}
}

VFG.Polyline.getPositions=function(points){
	if(points){
		var positions=JSON.parse(points);
		if(positions.length>=2){
			var Hierarchy=[];
			for(var i=0;i<positions.length;i++){
				Hierarchy.push(Cesium.Cartesian3.fromDegrees(positions[i].x*1,positions[i].y*1,positions[i].z*1));
			}
			return Hierarchy;
		}
	}else{
		return [];
	}
}

VFG.Polyline.getPolylineForAPI = function(data) {
	var _this=this;
	if(!data){
		return null;
	}
    var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(data.distanceDisplayConditionX,data.distanceDisplayConditionY);
    var material=VFG.Util.getMaterialForLine(data);
    if(!material){
		return null;
	}
    
    return{
        show: true,
        positions: data.positions?data.positions:[],
		width : data.width*1,
		loop:data.loop&&data.loop=='1'?true:false,
		clampToGround:data.clampToGround&&data.clampToGround=='1'?true:false,
		material:material?material:Cesium.Color.RED,
		distanceDisplayCondition : distanceDisplayCondition?distanceDisplayCondition:undefined,
		zIndex: data.sort*1,		
	}
};

VFG.Polyline.showOrHideEntityById=function(id,state){
	var Entity=this.Layers.entities.getById(id);
	if(Entity){
		Entity.show=state;
	}
}

VFG.Polyline.addPrimitive=function(){
}

;
///<jscompress sourcefile="VFGCircleRipplePrimitive.js" />
VFG.VFGCircleRipplePrimitive=function(viewer,option){
	this.option = Cesium.defaultValue(option, Cesium.defaultValue.EMPTY_OBJECT);
	if (!option) {
		console.log('参数必填!');
	}
	this.viewer=viewer;
	this.viewer=viewer;
}

VFG.VFGCircleRipplePrimitive.prototype.init=function(){
	var _this=this;
}


/**
 * 开始
 */
VFG.VFGCircleRipplePrimitive.prototype.start=function(){
	var _this=this;
	_this.viewer.clock.shouldAnimate = true;
}


VFG.VFGCircleRipplePrimitive.prototype.destroy=function(){
	var _this=this;
	_this.viewer.clock.onStop.removeEventListener(_this.complete);
}

;
///<jscompress sourcefile="VFGClassificationPrimitive.js" />
/**
 * 定义分类
 */
VFG.ClassificationPrimitive=function(option){
	this.option = Cesium.defaultValue(option, Cesium.defaultValue.EMPTY_OBJECT);
	if (!option) {
		console.log('参数必填!');
	}
	this.id=option.id||VFG.Util.getUuid();
	this.name=option.name||'未命名';
	this.isView=option.isView||'1';
	this.position=option.position;
	this.rotation=option.rotation;
	this.dimensions=option.dimensions;
	this.normalColor=option.normalColor? Cesium.Color.fromCssColorString(option.normalColor) :Cesium.Color.fromCssColorString('rgba(255,3,244,0.5)');
	this.hoverColor=option.hoverColor? Cesium.Color.fromCssColorString(option.hoverColor) :Cesium.Color.fromCssColorString('rgba(255,3,244,1)');
	this.init();
}

VFG.ClassificationPrimitive.prototype.init=function(){
	var _this=this;
	_this.primitive=new Cesium.ClassificationPrimitive({
		  geometryInstances: new Cesium.GeometryInstance({
		      geometry: Cesium.BoxGeometry.fromDimensions({
		            vertexFormat : Cesium.PerInstanceColorAppearance.VERTEX_FORMAT,  
			        dimensions: new Cesium.Cartesian3(((_this.dimensions&& _this.dimensions.x) || 5.0),((_this.dimensions&& _this.dimensions.y) || 5.0),((_this.dimensions&& _this.dimensions.z) || 5.0)),
		      }),
		      modelMatrix:_this.getModelMatrix(),
		      attributes: {
		        color:Cesium.ColorGeometryInstanceAttribute.fromColor((_this.isView && _this.isView=='1')?_this.normalColor:_this.normalColor.withAlpha(0.0)),
		        show: new Cesium.ShowGeometryInstanceAttribute(true),
		      },
		      id:_this.id,
	    }),
	 })
}

/**
 * 计算矩阵
 */
VFG.ClassificationPrimitive.prototype.getModelMatrix=function(){
	var position = Cesium.Cartesian3.fromDegrees(this.position.x*1,this.position.y*1,this.position.z*1);
    var heading = Cesium.Math.toRadians(((this.rotation&& this.rotation.x) || 0.0));
    var pitch = Cesium.Math.toRadians(((this.rotation&& this.rotation.y) || 0.0));
    var roll = Cesium.Math.toRadians(((this.rotation&& this.rotation.z) || 0.0));
	var modelMatrix = Cesium.Transforms.eastNorthUpToFixedFrame(position);
	var hprRotation = Cesium.Matrix3.fromHeadingPitchRoll(new Cesium.HeadingPitchRoll(heading, pitch, roll));
	var hpr = Cesium.Matrix4.fromRotationTranslation(hprRotation,new Cesium.Cartesian3(0.0, 0.0, 0.0));
	Cesium.Matrix4.multiply(modelMatrix, hpr, modelMatrix);
	return modelMatrix;
}
VFG.ClassificationPrimitive.prototype.setNormalColor=function(color){
	if(this.primitive){
	    var attributes = this.primitive.getGeometryInstanceAttributes(this.id);
	    if(attributes){
	    	this.normalColor=Cesium.Color.fromCssColorString(color)
	    	if(this.isView=='1'){
	    		attributes.color =Cesium.ColorGeometryInstanceAttribute.toValue(this.normalColor)
	    	}else{
	    		attributes.color =Cesium.ColorGeometryInstanceAttribute.toValue(this.normalColor.withAlpha(0.0))
	    	}
	    }
	}
}

VFG.ClassificationPrimitive.prototype.setHoverColor=function(color){
	this.hoverColor=Cesium.Color.fromCssColorString(color)
}

/**
 * 显示
 */
VFG.ClassificationPrimitive.prototype.setDisplay=function(isView){
	if(this.primitive){
		this.isView=isView;
	    var attributes = this.primitive.getGeometryInstanceAttributes(this.id);
	    if(attributes){
			if('1'==isView){
		    	attributes.color =Cesium.ColorGeometryInstanceAttribute.toValue(this.normalColor); 
			}else{
				attributes.color =Cesium.ColorGeometryInstanceAttribute.toValue(this.normalColor.withAlpha(0.0)); 
			}
	    }
	}
}

/**
 * 旋转
 */
VFG.ClassificationPrimitive.prototype.rotateFeature=function(rotation){
	this.rotation=rotation;
	if(this.primitive){
		this.primitive._primitive.modelMatrix=this.getModelMatrix();
		
	}
}

/**
 * 移动
 */
VFG.ClassificationPrimitive.prototype.translateFeature=function(position){
	this.position=position;
	if(this.primitive){
		this.primitive._primitive.modelMatrix=this.getModelMatrix();
	}
}

VFG.ClassificationPrimitive.prototype.setDimensions=function(dimensions){
	var _this=this;
	_this.dimensions=dimensions;
	_this.primitive=new Cesium.ClassificationPrimitive({
		  geometryInstances: new Cesium.GeometryInstance({
		      geometry: Cesium.BoxGeometry.fromDimensions({
		            vertexFormat : Cesium.PerInstanceColorAppearance.VERTEX_FORMAT,  
			        dimensions: new Cesium.Cartesian3(((_this.dimensions&& _this.dimensions.x) || 5.0),((_this.dimensions&& _this.dimensions.y) || 5.0),((_this.dimensions&& _this.dimensions.z) || 5.0)),
		      }),
		      modelMatrix:_this.getModelMatrix(),
		      attributes: {
		        color:Cesium.ColorGeometryInstanceAttribute.fromColor(_this.normalColor),
		        show: new Cesium.ShowGeometryInstanceAttribute(true),
		      },
		      id:_this.id,
	    }),
	 })
	return _this.primitive;
}

VFG.ClassificationPrimitive.prototype.enter=function(){
	if(this.primitive){
	    var attributes = this.primitive.getGeometryInstanceAttributes(this.id);
	    if(attributes){
	    	attributes.color =Cesium.ColorGeometryInstanceAttribute.toValue(this.hoverColor)
	    }
	}
}

VFG.ClassificationPrimitive.prototype.leave=function(){
	if(this.primitive){
	    var attributes = this.primitive.getGeometryInstanceAttributes(this.id);
	    if(attributes){
	    	if(this.isView=='1'){
	    		attributes.color =Cesium.ColorGeometryInstanceAttribute.toValue(this.normalColor)
	    	}else{
	    		attributes.color =Cesium.ColorGeometryInstanceAttribute.toValue(this.normalColor.withAlpha(0.0))
	    	}
	    }
	}
}
;
///<jscompress sourcefile="VFGHeatmapPrimitive.js" />
/*
 *  CesiumHeatmap.js v0.1 | Cesium Heatmap Library
 *  
 *  Works with heatmap.js v2.0.0: http://www.patrick-wied.at/static/heatmapjs/
 */
(function (window) {
	'use strict';

	function define_CesiumHeatmap() {
		var CesiumHeatmap = {
			defaults: {
				useEntitiesIfAvailable: true, //whether to use entities if a Viewer is supplied or always use an ImageryProvider
				minCanvasSize: 700,           // minimum size (in pixels) for the heatmap canvas
				maxCanvasSize: 2000,          // maximum size (in pixels) for the heatmap canvas
				radiusFactor: 60,             // data point size factor used if no radius is given (the greater of height and width divided by this number yields the used radius)
				spacingFactor: 1.5,           // extra space around the borders (point radius multiplied by this number yields the spacing)
				maxOpacity: 0.8,              // the maximum opacity used if not given in the heatmap options object
				minOpacity: 0.1,              // the minimum opacity used if not given in the heatmap options object
				blur: 0.85,                   // the blur used if not given in the heatmap options object
				gradient: {                   // the gradient used if not given in the heatmap options object
					'.3': 'blue',
					'.65': 'yellow',
					'.8': 'orange',
					'.95': 'red'
				},
			}
		};

		/*  Create a CesiumHeatmap instance
		 *
		 *  cesium:  the CesiumWidget or Viewer instance
		 *  bb:      the WGS84 bounding box like {north, east, south, west}
		 *  options: a heatmap.js options object (see http://www.patrick-wied.at/static/heatmapjs/docs.html#h337-create)
		 */
		CesiumHeatmap.create = function (cesium, bb, options) {
			var instance = new CHInstance(cesium, bb, options);
			return instance;
		};

		CesiumHeatmap._getContainer = function (width, height, id) {
			var c = document.createElement("div");
			if (id) {
				c.setAttribute("id", id);
			}
			c.setAttribute("style", "width: " + width + "px; height: " + height + "px; margin: 0px; display: none;");
			document.body.appendChild(c);
			return c;
		};

		CesiumHeatmap._getImageryProvider = function (instance) {
			//var n = (new Date()).getTime();
			var d = instance._heatmap.getDataURL();
			//console.log("Create data URL: " + ((new Date()).getTime() - n));

			//var n = (new Date()).getTime();
			var imgprov = new Cesium.SingleTileImageryProvider({
				url: d,
				rectangle: instance._rectangle
			});
			//console.log("Create imageryprovider: " + ((new Date()).getTime() - n));

			imgprov._tilingScheme = new Cesium.WebMercatorTilingScheme({
				rectangleSouthwestInMeters: new Cesium.Cartesian2(instance._mbounds.west, instance._mbounds.south),
				rectangleNortheastInMeters: new Cesium.Cartesian2(instance._mbounds.east, instance._mbounds.north)
			});

			return imgprov;
		};

		CesiumHeatmap._getID = function (len) {
			var text = "";
			var possible = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";

			for (var i = 0; i < ((len) ? len : 8); i++)
				text += possible.charAt(Math.floor(Math.random() * possible.length));

			return text;
		};

		var WMP = new Cesium.WebMercatorProjection();

		/*  Convert a WGS84 location into a mercator location
		 *
		 *  p: the WGS84 location like {x: lon, y: lat}
		 */
		CesiumHeatmap.wgs84ToMercator = function (p) {
			var mp = WMP.project(Cesium.Cartographic.fromDegrees(p.x, p.y));
			return {
				x: mp.x,
				y: mp.y
			};
		};

		/*  Convert a WGS84 bounding box into a mercator bounding box
		 *
		 *  bb: the WGS84 bounding box like {north, east, south, west}
		 */
		CesiumHeatmap.wgs84ToMercatorBB = function (bb) {
			var sw = WMP.project(Cesium.Cartographic.fromDegrees(bb.west, bb.south));
			var ne = WMP.project(Cesium.Cartographic.fromDegrees(bb.east, bb.north));
			return {
				north: ne.y,
				east: ne.x,
				south: sw.y,
				west: sw.x
			};
		};

		/*  Convert a mercator location into a WGS84 location
		 *
		 *  p: the mercator lcation like {x, y}
		 */
		CesiumHeatmap.mercatorToWgs84 = function (p) {
			var wp = WMP.unproject(new Cesium.Cartesian3(p.x, p.y));
			return {
				x: wp.longitude,
				y: wp.latitude
			};
		};

		/*  Convert a mercator bounding box into a WGS84 bounding box
		 *
		 *  bb: the mercator bounding box like {north, east, south, west}
		 */
		CesiumHeatmap.mercatorToWgs84BB = function (bb) {
			var sw = WMP.unproject(new Cesium.Cartesian3(bb.west, bb.south));
			var ne = WMP.unproject(new Cesium.Cartesian3(bb.east, bb.north));
			return {
				north: this.rad2deg(ne.latitude),
				east: this.rad2deg(ne.longitude),
				south: this.rad2deg(sw.latitude),
				west: this.rad2deg(sw.longitude)
			};
		};

		/*  Convert degrees into radians
		 *
		 *  d: the degrees to be converted to radians
		 */
		CesiumHeatmap.deg2rad = function (d) {
			var r = d * (Math.PI / 180.0);
			return r;
		};

		/*  Convert radians into degrees
		 *
		 *  r: the radians to be converted to degrees
		 */
		CesiumHeatmap.rad2deg = function (r) {
			var d = r / (Math.PI / 180.0);
			return d;
		};

		return CesiumHeatmap;
	}

	if (typeof(CesiumHeatmap) === 'undefined') {
		window.CesiumHeatmap = define_CesiumHeatmap();
	} else {
		console.log("CesiumHeatmap already defined.");
	}
})(window);

/*  Initiate a CesiumHeatmap instance
 *
 *  c:  CesiumWidget instance
 *  bb: a WGS84 bounding box like {north, east, south, west}
 *  o:  a heatmap.js options object (see http://www.patrick-wied.at/static/heatmapjs/docs.html#h337-create)
 */
function CHInstance(c, bb, o) {
	if (!bb) {
		return null;
	}
	if (!o) {
		o = {};
	}

	this._cesium = c;
	this._options = o;
	this._id = CesiumHeatmap._getID();

	this._options.gradient = ((this._options.gradient) ? this._options.gradient : CesiumHeatmap.defaults.gradient);
	this._options.maxOpacity = ((this._options.maxOpacity) ? this._options.maxOpacity : CesiumHeatmap.defaults.maxOpacity);
	this._options.minOpacity = ((this._options.minOpacity) ? this._options.minOpacity : CesiumHeatmap.defaults.minOpacity);
	this._options.blur = ((this._options.blur) ? this._options.blur : CesiumHeatmap.defaults.blur);

	this._mbounds = CesiumHeatmap.wgs84ToMercatorBB(bb);
	this._setWidthAndHeight(this._mbounds);

	this._options.radius = Math.round((this._options.radius) ? this._options.radius : ((this.width > this.height) ? this.width / CesiumHeatmap.defaults.radiusFactor : this.height / CesiumHeatmap.defaults.radiusFactor));

	this._spacing = this._options.radius * CesiumHeatmap.defaults.spacingFactor;
	this._xoffset = this._mbounds.west;
	this._yoffset = this._mbounds.south;

	this.width = Math.round(this.width + this._spacing * 2);
	this.height = Math.round(this.height + this._spacing * 2);

	this._mbounds.west -= this._spacing * this._factor;
	this._mbounds.east += this._spacing * this._factor;
	this._mbounds.south -= this._spacing * this._factor;
	this._mbounds.north += this._spacing * this._factor;

	this.bounds = CesiumHeatmap.mercatorToWgs84BB(this._mbounds);

	this._rectangle = Cesium.Rectangle.fromDegrees(this.bounds.west, this.bounds.south, this.bounds.east, this.bounds.north);
	this._container = CesiumHeatmap._getContainer(this.width, this.height, this._id);
	this._options.container = this._container;
	this._heatmap = h337.create(this._options);
	this._container.children[0].setAttribute("id", this._id + "-hm");
}

/*  Convert a WGS84 location to the corresponding heatmap location
 *
 *  p: a WGS84 location like {x:lon, y:lat}
 */
CHInstance.prototype.wgs84PointToHeatmapPoint = function (p) {
	return this.mercatorPointToHeatmapPoint(CesiumHeatmap.wgs84ToMercator(p));
};

/*  Convert a mercator location to the corresponding heatmap location
 *
 *  p: a WGS84 location like {x: lon, y:lat}
 */
CHInstance.prototype.mercatorPointToHeatmapPoint = function (p) {
	var pn = {};

	pn.x = Math.round((p.x - this._xoffset) / this._factor + this._spacing);
	pn.y = Math.round((p.y - this._yoffset) / this._factor + this._spacing);
	pn.y = this.height - pn.y;

	return pn;
};

CHInstance.prototype._setWidthAndHeight = function (mbb) {
	this.width = ((mbb.east > 0 && mbb.west < 0) ? mbb.east + Math.abs(mbb.west) : Math.abs(mbb.east - mbb.west));
	this.height = ((mbb.north > 0 && mbb.south < 0) ? mbb.north + Math.abs(mbb.south) : Math.abs(mbb.north - mbb.south));
	this._factor = 1;

	if (this.width > this.height && this.width > CesiumHeatmap.defaults.maxCanvasSize) {
		this._factor = this.width / CesiumHeatmap.defaults.maxCanvasSize;

		if (this.height / this._factor < CesiumHeatmap.defaults.minCanvasSize) {
			this._factor = this.height / CesiumHeatmap.defaults.minCanvasSize;
		}
	} else if (this.height > this.width && this.height > CesiumHeatmap.defaults.maxCanvasSize) {
		this._factor = this.height / CesiumHeatmap.defaults.maxCanvasSize;

		if (this.width / this._factor < CesiumHeatmap.defaults.minCanvasSize) {
			this._factor = this.width / CesiumHeatmap.defaults.minCanvasSize;
		}
	} else if (this.width < this.height && this.width < CesiumHeatmap.defaults.minCanvasSize) {
		this._factor = this.width / CesiumHeatmap.defaults.minCanvasSize;

		if (this.height / this._factor > CesiumHeatmap.defaults.maxCanvasSize) {
			this._factor = this.height / CesiumHeatmap.defaults.maxCanvasSize;
		}
	} else if (this.height < this.width && this.height < CesiumHeatmap.defaults.minCanvasSize) {
		this._factor = this.height / CesiumHeatmap.defaults.minCanvasSize;

		if (this.width / this._factor > CesiumHeatmap.defaults.maxCanvasSize) {
			this._factor = this.width / CesiumHeatmap.defaults.maxCanvasSize;
		}
	}

	this.width = this.width / this._factor;
	this.height = this.height / this._factor;
};

/*  Set an array of heatmap locations
 *
 *  min:  the minimum allowed value for the data values
 *  max:  the maximum allowed value for the data values
 *  data: an array of data points in heatmap coordinates and values like {x, y, value}
 */
CHInstance.prototype.setData = function (min, max, data) {
	if (data && data.length > 0 && min !== null && min !== false && max !== null && max !== false) {
		this._heatmap.setData({
			min: min,
			max: max,
			data: data
		});

		this.updateLayer();
		return true;
	}

	return false;
};

/*  Set an array of WGS84 locations
 *
 *  min:  the minimum allowed value for the data values
 *  max:  the maximum allowed value for the data values
 *  data: an array of data points in WGS84 coordinates and values like { x:lon, y:lat, value }
 */
CHInstance.prototype.setWGS84Data = function (min, max, data) {
	if (data && data.length > 0 && min !== null && min !== false && max !== null && max !== false) {
		var convdata = [];

		for (var i = 0; i < data.length; i++) {
			var gp = data[i];

			var hp = this.wgs84PointToHeatmapPoint(gp);
			if (gp.value || gp.value === 0) {
				hp.value = gp.value;
			}

			convdata.push(hp);
		}

		return this.setData(min, max, convdata);
	}

	return false;
};

/*  Set whether or not the heatmap is shown on the map
 *
 *  s: true means the heatmap is shown, false means the heatmap is hidden
 */
CHInstance.prototype.show = function (s) {
	if (this._layer) {
		this._layer.show = s;
	}
};

/*  Update/(re)draw the heatmap
 */
CHInstance.prototype.updateLayer = function () {

	// only works with a Viewer instance since the cesiumWidget
	// instance doesn't contain an entities property
	if (CesiumHeatmap.defaults.useEntitiesIfAvailable && this._cesium.entities) {
		if (this._layer) {
			this._cesium.entities.remove(this._layer);
		}

		// Work around issue with material rendering in Cesium
		// provided by https://github.com/criis
		material = new Cesium.ImageMaterialProperty({
			image: this._heatmap._renderer.canvas,
		});
		if (Cesium.VERSION >= "1.21") {
			material.transparent = true;
		} else if (Cesium.VERSION >= "1.16") {
			material.alpha = 0.99;
		}

		this._layer = this._cesium.entities.add({
			show: true,
			rectangle: {
				coordinates: this._rectangle,
				material: material
			}
		});
	} else {
		if (this._layer) {
			this._cesium.scene.imageryLayers.remove(this._layer);
		}

		this._layer = this._cesium.scene.imageryLayers.addImageryProvider(CesiumHeatmap._getImageryProvider(this));
	}
};

/**
 * 移除
 */
CHInstance.prototype.removeLayer = function () {
	if (CesiumHeatmap.defaults.useEntitiesIfAvailable && this._cesium.entities) {
		if (this._layer) {
			this._cesium.entities.remove(this._layer);
		}
	} else {
		if (this._layer) {
			this._cesium.scene.imageryLayers.remove(this._layer);
		}

	}
};



/*  DON'T TOUCH:
 *
 *  heatmap.js v2.0.0 | JavaScript Heatmap Library: http://www.patrick-wied.at/static/heatmapjs/
 *
 *  Copyright 2008-2014 Patrick Wied <heatmapjs@patrick-wied.at> - All rights reserved.
 *  Dual licensed under MIT and Beerware license
 *
 *  :: 2014-10-31 21:16
 */
(function (a, b, c) {
	if (typeof module !== "undefined" && module.exports) {
		module.exports = c()
	} else if (typeof define === "function" && define.amd) {
		define(c)
	} else {
		b[a] = c()
	}
})("h337", this, function () {
	var a = {
		defaultRadius: 40,
		defaultRenderer: "canvas2d",
		defaultGradient: {.25: "rgb(0,0,255)", .55: "rgb(0,255,0)", .85: "yellow", 1: "rgb(255,0,0)"},
		defaultMaxOpacity: 1,
		defaultMinOpacity: 0,
		defaultBlur: .85,
		defaultXField: "x",
		defaultYField: "y",
		defaultValueField: "value",
		plugins: {}
	};
	var b = function h() {
		var b = function d(a) {
			this._coordinator = {};
			this._data = [];
			this._radi = [];
			this._min = 0;
			this._max = 1;
			this._xField = a["xField"] || a.defaultXField;
			this._yField = a["yField"] || a.defaultYField;
			this._valueField = a["valueField"] || a.defaultValueField;
			if (a["radius"]) {
				this._cfgRadius = a["radius"]
			}
		};
		var c = a.defaultRadius;
		b.prototype = {
			_organiseData: function (a, b) {
				var d = a[this._xField];
				var e = a[this._yField];
				var f = this._radi;
				var g = this._data;
				var h = this._max;
				var i = this._min;
				var j = a[this._valueField] || 1;
				var k = a.radius || this._cfgRadius || c;
				if (!g[d]) {
					g[d] = [];
					f[d] = []
				}
				if (!g[d][e]) {
					g[d][e] = j;
					f[d][e] = k
				} else {
					g[d][e] += j
				}
				if (g[d][e] > h) {
					if (!b) {
						this._max = g[d][e]
					} else {
						this.setDataMax(g[d][e])
					}
					return false
				} else {
					return {x: d, y: e, value: j, radius: k, min: i, max: h}
				}
			}, _unOrganizeData: function () {
				var a = [];
				var b = this._data;
				var c = this._radi;
				for (var d in b) {
					for (var e in b[d]) {
						a.push({x: d, y: e, radius: c[d][e], value: b[d][e]})
					}
				}
				return {min: this._min, max: this._max, data: a}
			}, _onExtremaChange: function () {
				this._coordinator.emit("extremachange", {min: this._min, max: this._max})
			}, addData: function () {
				if (arguments[0].length > 0) {
					var a = arguments[0];
					var b = a.length;
					while (b--) {
						this.addData.call(this, a[b])
					}
				} else {
					var c = this._organiseData(arguments[0], true);
					if (c) {
						this._coordinator.emit("renderpartial", {min: this._min, max: this._max, data: [c]})
					}
				}
				return this
			}, setData: function (a) {
				var b = a.data;
				var c = b.length;
				this._data = [];
				this._radi = [];
				for (var d = 0; d < c; d++) {
					this._organiseData(b[d], false)
				}
				this._max = a.max;
				this._min = a.min || 0;
				this._onExtremaChange();
				this._coordinator.emit("renderall", this._getInternalData());
				return this
			}, removeData: function () {
			}, setDataMax: function (a) {
				this._max = a;
				this._onExtremaChange();
				this._coordinator.emit("renderall", this._getInternalData());
				return this
			}, setDataMin: function (a) {
				this._min = a;
				this._onExtremaChange();
				this._coordinator.emit("renderall", this._getInternalData());
				return this
			}, setCoordinator: function (a) {
				this._coordinator = a
			}, _getInternalData: function () {
				return {max: this._max, min: this._min, data: this._data, radi: this._radi}
			}, getData: function () {
				return this._unOrganizeData()
			}
		};
		return b
	}();
	var c = function i() {
		var a = function (a) {
			var b = a.gradient || a.defaultGradient;
			var c = document.createElement("canvas");
			var d = c.getContext("2d");
			c.width = 256;
			c.height = 1;
			var e = d.createLinearGradient(0, 0, 256, 1);
			for (var f in b) {
				e.addColorStop(f, b[f])
			}
			d.fillStyle = e;
			d.fillRect(0, 0, 256, 1);
			return d.getImageData(0, 0, 256, 1).data
		};
		var b = function (a, b) {
			var c = document.createElement("canvas");
			var d = c.getContext("2d");
			var e = a;
			var f = a;
			c.width = c.height = a * 2;
			if (b == 1) {
				d.beginPath();
				d.arc(e, f, a, 0, 2 * Math.PI, false);
				d.fillStyle = "rgba(0,0,0,1)";
				d.fill()
			} else {
				var g = d.createRadialGradient(e, f, a * b, e, f, a);
				g.addColorStop(0, "rgba(0,0,0,1)");
				g.addColorStop(1, "rgba(0,0,0,0)");
				d.fillStyle = g;
				d.fillRect(0, 0, 2 * a, 2 * a)
			}
			return c
		};
		var c = function (a) {
			var b = [];
			var c = a.min;
			var d = a.max;
			var e = a.radi;
			var a = a.data;
			var f = Object.keys(a);
			var g = f.length;
			while (g--) {
				var h = f[g];
				var i = Object.keys(a[h]);
				var j = i.length;
				while (j--) {
					var k = i[j];
					var l = a[h][k];
					var m = e[h][k];
					b.push({x: h, y: k, value: l, radius: m})
				}
			}
			return {min: c, max: d, data: b}
		};

		function d(b) {
			var c = b.container;
			var d = this.shadowCanvas = document.createElement("canvas");
			var e = this.canvas = b.canvas || document.createElement("canvas");
			var f = this._renderBoundaries = [1e4, 1e4, 0, 0];
			var g = getComputedStyle(b.container) || {};
			e.className = "heatmap-canvas";
			this._width = e.width = d.width = +g.width.replace(/px/, "");
			this._height = e.height = d.height = +g.height.replace(/px/, "");
			this.shadowCtx = d.getContext("2d");
			this.ctx = e.getContext("2d");
			e.style.cssText = d.style.cssText = "position:absolute;left:0;top:0;";
			c.style.position = "relative";
			c.appendChild(e);
			this._palette = a(b);
			this._templates = {};
			this._setStyles(b)
		}

		d.prototype = {
			renderPartial: function (a) {
				this._drawAlpha(a);
				this._colorize()
			}, renderAll: function (a) {
				this._clear();
				this._drawAlpha(c(a));
				this._colorize()
			}, _updateGradient: function (b) {
				this._palette = a(b)
			}, updateConfig: function (a) {
				if (a["gradient"]) {
					this._updateGradient(a)
				}
				this._setStyles(a)
			}, setDimensions: function (a, b) {
				this._width = a;
				this._height = b;
				this.canvas.width = this.shadowCanvas.width = a;
				this.canvas.height = this.shadowCanvas.height = b
			}, _clear: function () {
				this.shadowCtx.clearRect(0, 0, this._width, this._height);
				this.ctx.clearRect(0, 0, this._width, this._height)
			}, _setStyles: function (a) {
				this._blur = a.blur == 0 ? 0 : a.blur || a.defaultBlur;
				if (a.backgroundColor) {
					this.canvas.style.backgroundColor = a.backgroundColor
				}
				this._opacity = (a.opacity || 0) * 255;
				this._maxOpacity = (a.maxOpacity || a.defaultMaxOpacity) * 255;
				this._minOpacity = (a.minOpacity || a.defaultMinOpacity) * 255;
				this._useGradientOpacity = !!a.useGradientOpacity
			}, _drawAlpha: function (a) {
				var c = this._min = a.min;
				var d = this._max = a.max;
				var a = a.data || [];
				var e = a.length;
				var f = 1 - this._blur;
				while (e--) {
					var g = a[e];
					var h = g.x;
					var i = g.y;
					var j = g.radius;
					var k = Math.min(g.value, d);
					var l = h - j;
					var m = i - j;
					var n = this.shadowCtx;
					var o;
					if (!this._templates[j]) {
						this._templates[j] = o = b(j, f)
					} else {
						o = this._templates[j]
					}
					n.globalAlpha = (k - c) / (d - c);
					n.drawImage(o, l, m);
					if (l < this._renderBoundaries[0]) {
						this._renderBoundaries[0] = l
					}
					if (m < this._renderBoundaries[1]) {
						this._renderBoundaries[1] = m
					}
					if (l + 2 * j > this._renderBoundaries[2]) {
						this._renderBoundaries[2] = l + 2 * j
					}
					if (m + 2 * j > this._renderBoundaries[3]) {
						this._renderBoundaries[3] = m + 2 * j
					}
				}
			}, _colorize: function () {
				var a = this._renderBoundaries[0];
				var b = this._renderBoundaries[1];
				var c = this._renderBoundaries[2] - a;
				var d = this._renderBoundaries[3] - b;
				var e = this._width;
				var f = this._height;
				var g = this._opacity;
				var h = this._maxOpacity;
				var i = this._minOpacity;
				var j = this._useGradientOpacity;
				if (a < 0) {
					a = 0
				}
				if (b < 0) {
					b = 0
				}
				if (a + c > e) {
					c = e - a
				}
				if (b + d > f) {
					d = f - b
				}
				var k = this.shadowCtx.getImageData(a, b, c, d);
				var l = k.data;
				var m = l.length;
				var n = this._palette;
				for (var o = 3; o < m; o += 4) {
					var p = l[o];
					var q = p * 4;
					if (!q) {
						continue
					}
					var r;
					if (g > 0) {
						r = g
					} else {
						if (p < h) {
							if (p < i) {
								r = i
							} else {
								r = p
							}
						} else {
							r = h
						}
					}
					l[o - 3] = n[q];
					l[o - 2] = n[q + 1];
					l[o - 1] = n[q + 2];
					l[o] = j ? n[q + 3] : r
				}
				k.data = l;
				this.ctx.putImageData(k, a, b);
				this._renderBoundaries = [1e3, 1e3, 0, 0]
			}, getValueAt: function (a) {
				var b;
				var c = this.shadowCtx;
				var d = c.getImageData(a.x, a.y, 1, 1);
				var e = d.data[3];
				var f = this._max;
				var g = this._min;
				b = Math.abs(f - g) * (e / 255) >> 0;
				return b
			}, getDataURL: function () {
				return this.canvas.toDataURL()
			}
		};
		return d
	}();
	var d = function j() {
		var b = false;
		if (a["defaultRenderer"] === "canvas2d") {
			b = c
		}
		return b
	}();
	var e = {
		merge: function () {
			var a = {};
			var b = arguments.length;
			for (var c = 0; c < b; c++) {
				var d = arguments[c];
				for (var e in d) {
					a[e] = d[e]
				}
			}
			return a
		}
	};
	var f = function k() {
		var c = function h() {
			function a() {
				this.cStore = {}
			}

			a.prototype = {
				on: function (a, b, c) {
					var d = this.cStore;
					if (!d[a]) {
						d[a] = []
					}
					d[a].push(function (a) {
						return b.call(c, a)
					})
				}, emit: function (a, b) {
					var c = this.cStore;
					if (c[a]) {
						var d = c[a].length;
						for (var e = 0; e < d; e++) {
							var f = c[a][e];
							f(b)
						}
					}
				}
			};
			return a
		}();
		var f = function (a) {
			var b = a._renderer;
			var c = a._coordinator;
			var d = a._store;
			c.on("renderpartial", b.renderPartial, b);
			c.on("renderall", b.renderAll, b);
			c.on("extremachange", function (b) {
				a._config.onExtremaChange && a._config.onExtremaChange({
					min: b.min,
					max: b.max,
					gradient: a._config["gradient"] || a._config["defaultGradient"]
				})
			});
			d.setCoordinator(c)
		};

		function g() {
			var g = this._config = e.merge(a, arguments[0] || {});
			this._coordinator = new c;
			if (g["plugin"]) {
				var h = g["plugin"];
				if (!a.plugins[h]) {
					throw new Error("Plugin '" + h + "' not found. Maybe it was not registered.")
				} else {
					var i = a.plugins[h];
					this._renderer = new i.renderer(g);
					this._store = new i.store(g)
				}
			} else {
				this._renderer = new d(g);
				this._store = new b(g)
			}
			f(this)
		}

		g.prototype = {
			addData: function () {
				this._store.addData.apply(this._store, arguments);
				return this
			}, removeData: function () {
				this._store.removeData && this._store.removeData.apply(this._store, arguments);
				return this
			}, setData: function () {
				this._store.setData.apply(this._store, arguments);
				return this
			}, setDataMax: function () {
				this._store.setDataMax.apply(this._store, arguments);
				return this
			}, setDataMin: function () {
				this._store.setDataMin.apply(this._store, arguments);
				return this
			}, configure: function (a) {
				this._config = e.merge(this._config, a);
				this._renderer.updateConfig(this._config);
				this._coordinator.emit("renderall", this._store._getInternalData());
				return this
			}, repaint: function () {
				this._coordinator.emit("renderall", this._store._getInternalData());
				return this
			}, getData: function () {
				return this._store.getData()
			}, getDataURL: function () {
				return this._renderer.getDataURL()
			}, getValueAt: function (a) {
				if (this._store.getValueAt) {
					return this._store.getValueAt(a)
				} else if (this._renderer.getValueAt) {
					return this._renderer.getValueAt(a)
				} else {
					return null
				}
			}
		};
		return g
	}();
	var g = {
		create: function (a) {
			return new f(a)
		}, register: function (b, c) {
			a.plugins[b] = c
		}
	};
	return g
});;
///<jscompress sourcefile="VFGTipPrimitive.js" />
/*  *  *  *  *  *  *  *  *  *  *
 *     Tip      *
 *  *  *  *  *  *  *  *  *  *  */
!function(e, t) {
	"object" == typeof exports && "object" == typeof module ? module.exports = t(require("Cesium"))
			: "function" == typeof define && define.amd ? define([ "Cesium" ],
					t)
					: "object" == typeof exports ? exports.CesiumMQTT = t(require("Cesium"))
							: e.VFGTip = t(e.Cesium)
}("undefined" != typeof self ? self : this, function(cesium) {
	function _(viewer, options) {
		this.viewer = viewer;
		this.options = options;
		this.frameDiv=this.viewer.cesiumWidget.container;
		this.isInit=false;
		this.init();
	}
	_.prototype.init = function() {
		var _self = this;
	    if (_self.isInit) { return; }
	    var div = document.createElement('DIV');
	    div.className = "toolTip-left";
	    var title = document.createElement('DIV');
	    title.className = "tooltipdiv-inner";
	    div.appendChild(title);
	    _self._div = div;
	    _self._title = title;
	    _self.frameDiv.appendChild(div);
	    _self.isInit = true;
	};
	_.prototype.setVisible = function(visible) {
		var _self = this;
	    if (!_self.isInit) { return; }
	    _self._div.style.display = visible ? 'block' : 'none';
	};
	_.prototype.showAt = function (position, message) {
		var _self = this;
	    if (!_self.isInit) { return; }
	    if (position && message) {
	    	_self.setVisible(true);
	    	_self._title.innerHTML = message;
	    	_self._div.style.position = "absolute"
	    	_self._div.style.left = position.x + 20 + "px";
	    	_self._div.style.top = (position.y - this._div.clientHeight/2) + "px";
	    }
    };
	_.prototype.destroy = function() {
		var _self = this;
		if( _self._div){
			$( _self._div).remove();
		}
		if( _self._title){
			$( _self._title).remove();
		}
		return Cesium.destroyObject(this);
	};
	VFG.Tip = _;
});
///<jscompress sourcefile="VFGGeojsonProvider.js" />

var defaultColor = new Cesium.Color(1.0, 1.0, 1.0, 0.4);
var defaultGlowColor = new Cesium.Color(0.0, 1.0, 0.0, 0.05);
var defaultBackgroundColor = new Cesium.Color(0.0, 0.5, 0.0, 0.2);

function VFGGeojsonProvider(viewer,options) {
  options = Cesium.defaultValue(options, Cesium.defaultValue.EMPTY_OBJECT);

  this._tilingScheme = Cesium.defined(options.tilingScheme) ? options.tilingScheme : new Cesium.GeographicTilingScheme({ ellipsoid: options.ellipsoid });
  this._cells = Cesium.defaultValue(options.cells, 8);
  this._color = Cesium.defaultValue(options.color, defaultColor);
  this._glowColor = Cesium.defaultValue(options.glowColor, defaultGlowColor);
  this._glowWidth = Cesium.defaultValue(options.glowWidth, 6);
  this._backgroundColor = Cesium.defaultValue(
    options.backgroundColor,
    defaultBackgroundColor
  );
  this._errorEvent = new Cesium.Event();

  this._tileWidth = Cesium.defaultValue(options.tileWidth, 256);
  this._tileHeight = Cesium.defaultValue(options.tileHeight, 256);

  this._canvasSize = Cesium.defaultValue(options.canvasSize, 256);

  this._canvas = this._createGridCanvas();
  this._readyPromise = Cesium.when.resolve(true);
  this._cacheMap=new Map();
  this._viewer=viewer;
  this._url=options.url;
  this._uri=options.uri;
  this._sceneId=options.sceneId;
  this._minLevel=options.minLevel*1||11;
  this._maxLevel=options.maxLevel*1||18;
  var _this=this;
  this._curCacheMap=new Map();
  this._tempCacheMap=new Map();
  var helper = new Cesium.EventHelper();
}

Object.defineProperties(VFGGeojsonProvider.prototype, {
  /**
   * Gets the proxy used by this provider.
   * @memberof VFGGeojsonProvider.prototype
   * @type {Proxy}
   * @readonly
   */
  proxy: {
    get: function () {
      return undefined;
    },
  },

  /**
   * Gets the width of each tile, in pixels. This function should
   * not be called before {@link VFGGeojsonProvider#ready} returns true.
   * @memberof VFGGeojsonProvider.prototype
   * @type {Number}
   * @readonly
   */
  tileWidth: {
    get: function () {
      return this._tileWidth;
    },
  },

  /**
   * Gets the height of each tile, in pixels.  This function should
   * not be called before {@link VFGGeojsonProvider#ready} returns true.
   * @memberof VFGGeojsonProvider.prototype
   * @type {Number}
   * @readonly
   */
  tileHeight: {
    get: function () {
      return this._tileHeight;
    },
  },

  /**
   * Gets the maximum level-of-detail that can be requested.  This function should
   * not be called before {@link VFGGeojsonProvider#ready} returns true.
   * @memberof VFGGeojsonProvider.prototype
   * @type {Number}
   * @readonly
   */
  maximumLevel: {
    get: function () {
      return undefined;
    },
  },

  /**
   * Gets the minimum level-of-detail that can be requested.  This function should
   * not be called before {@link VFGGeojsonProvider#ready} returns true.
   * @memberof VFGGeojsonProvider.prototype
   * @type {Number}
   * @readonly
   */
  minimumLevel: {
    get: function () {
      return undefined;
    },
  },

  /**
   * Gets the tiling scheme used by this provider.  This function should
   * not be called before {@link VFGGeojsonProvider#ready} returns true.
   * @memberof VFGGeojsonProvider.prototype
   * @type {TilingScheme}
   * @readonly
   */
  tilingScheme: {
    get: function () {
      return this._tilingScheme;
    },
  },

  /**
   * Gets the rectangle, in radians, of the imagery provided by this instance.  This function should
   * not be called before {@link VFGGeojsonProvider#ready} returns true.
   * @memberof VFGGeojsonProvider.prototype
   * @type {Rectangle}
   * @readonly
   */
  rectangle: {
    get: function () {
      return this._tilingScheme.rectangle;
    },
  },

  /**
   * Gets the tile discard policy.  If not undefined, the discard policy is responsible
   * for filtering out "missing" tiles via its shouldDiscardImage function.  If this function
   * returns undefined, no tiles are filtered.  This function should
   * not be called before {@link VFGGeojsonProvider#ready} returns true.
   * @memberof VFGGeojsonProvider.prototype
   * @type {TileDiscardPolicy}
   * @readonly
   */
  tileDiscardPolicy: {
    get: function () {
      return undefined;
    },
  },

  /**
   * Gets an event that is raised when the imagery provider encounters an asynchronous error.  By subscribing
   * to the event, you will be notified of the error and can potentially recover from it.  Event listeners
   * are passed an instance of {@link TileProviderError}.
   * @memberof VFGGeojsonProvider.prototype
   * @type {Event}
   * @readonly
   */
  errorEvent: {
    get: function () {
      return this._errorEvent;
    },
  },

  /**
   * Gets a value indicating whether or not the provider is ready for use.
   * @memberof VFGGeojsonProvider.prototype
   * @type {Boolean}
   * @readonly
   */
  ready: {
    get: function () {
      return true;
    },
  },

  /**
   * Gets a promise that resolves to true when the provider is ready for use.
   * @memberof VFGGeojsonProvider.prototype
   * @type {Promise.<Boolean>}
   * @readonly
   */
  readyPromise: {
    get: function () {
      return this._readyPromise;
    },
  },

  /**
   * Gets the credit to display when this imagery provider is active.  Typically this is used to credit
   * the source of the imagery.  This function should not be called before {@link VFGGeojsonProvider#ready} returns true.
   * @memberof VFGGeojsonProvider.prototype
   * @type {Credit}
   * @readonly
   */
  credit: {
    get: function () {
      return undefined;
    },
  },

  /**
   * Gets a value indicating whether or not the images provided by this imagery provider
   * include an alpha channel.  If this property is false, an alpha channel, if present, will
   * be ignored.  If this property is true, any images without an alpha channel will be treated
   * as if their alpha is 1.0 everywhere.  When this property is false, memory usage
   * and texture upload time are reduced.
   * @memberof VFGGeojsonProvider.prototype
   * @type {Boolean}
   * @readonly
   */
  hasAlphaChannel: {
    get: function () {
      return true;
    },
  },
});

/**
 * Draws a grid of lines into a canvas.
 */
VFGGeojsonProvider.prototype._drawGrid = function (context) {
  var minPixel = 0;
  var maxPixel = this._canvasSize;
  for (var x = 0; x <= this._cells; ++x) {
    var nx = x / this._cells;
    var val = 1 + nx * (maxPixel - 1);

    context.moveTo(val, minPixel);
    context.lineTo(val, maxPixel);
    context.moveTo(minPixel, val);
    context.lineTo(maxPixel, val);
  }
  context.stroke();
};

/**
 * Render a grid into a canvas with background and glow
 */
VFGGeojsonProvider.prototype._createGridCanvas = function () {
  var canvas = document.createElement("canvas");
  canvas.width = this._canvasSize;
  canvas.height = this._canvasSize;

  return canvas;
};

/**
 * Gets the credits to be displayed when a given tile is displayed.
 *
 * @param {Number} x The tile X coordinate.
 * @param {Number} y The tile Y coordinate.
 * @param {Number} level The tile level;
 * @returns {Credit[]} The credits to be displayed when the tile is displayed.
 *
 * @exception {DeveloperError} <code>getTileCredits</code> must not be called before the imagery provider is ready.
 */
VFGGeojsonProvider.prototype.getTileCredits = function (x, y, level) {
  return undefined;
};

VFGGeojsonProvider.prototype.requestImage = function (x, y, level, request) {
	var _this=this;
	var key="{x}-{y}-{z}".replace('{x}', x).replace('{y}', y).replace('{z}', level);
	
	var url=_this._url;
	  url=url.replace('{x}', x).replace('{y}', y).replace('{z}', level);
	  $.ajax({
	       url:url,
	       cache: false,
	       async: true,
	       success: function(data) {
	           	Cesium.GeoJsonDataSource.load(data).then(function(dataSource) {
	           		var entities=dataSource.entities.values;
	           		for(var i=0;i<entities.length;i++){
	           			VFG.Point.PointPrimitiveCollection.add({
	      				  id: entities[i].id,
	      				  name: entities[i].name,
	      		          pixelSize: 5,
	      		          color: Cesium.Color.RED,
	      		          color :new Cesium.Color ( 255 , 255 , 0 , 1 ),
	      		          outlineColor : Cesium.Color.YELLOW,
	      		          outlineWidth :2,
	      		          position: entities[i].position.getValue()
	           			})
	           			
	           		}
	        	});
	       },
	       error: function(data) {
	       }
	  });
	
	
	if(level>=this._minLevel && this._maxLevel>=level){
	}

  return this._canvas;
};


VFGGeojsonProvider.prototype.pickFeatures = function (
  x,
  y,
  level,
  longitude,
  latitude
) {
  return undefined;
};
;
///<jscompress sourcefile="VFGHeatmapImageryProvider.js" />
// /*
//  *  How to add HeatmapImageryProvider to Cesium:
//  *  
//  *  1. Add the class (define - return HeatmapImageryProvider) to Cesium.js after the definition of define and before the definition of Cesium.
//  *  2. Add './Scene/HeatmapImageryProvider' as the first value in the second parameter of the definition call of Cesium (on the line starting with "define('Cesium',[").
//  *  3. Add 'Scene_HeatmapImageryProvider' as the first value in the third parameter of the definition call of Cesium (on the line starting with "define('Cesium',[").
//  *  4. Add 'Cesium['HeatmapImageryProvider'] = Scene_HeatmapImageryProvider;' to the body of the definition call of Cesium (after the line starting with "var Cesium = {").
//  *  5. Make sure heatmap.js in included and available before using HeatmapImageryProvider.
//  *
//  */

// /*global define*/
// define('Scene/HeatmapImageryProvider',[
//         '../Core/Credit',
//         '../Core/defaultValue',
//         '../Core/defined',
//         '../Core/defineProperties',
//         '../Core/DeveloperError',
//         '../Core/Event',
//         '../Core/GeographicTilingScheme',
//         '../Core/Rectangle',
//         '../Core/TileProviderError'
//     ], function(
//         Credit,
//         defaultValue,
//         defined,
//         defineProperties,
//         DeveloperError,
//         Event,
//         GeographicTilingScheme,
//         Rectangle,
//         TileProviderError) {
//     "use strict";

//     /**
//      * Provides a single, top-level imagery tile.  The single image is assumed to use a
//      * {@link GeographicTilingScheme}.

//      *
//      * @alias HeatmapImageryProvider
//      * @constructor
//      *
//      * @param {Object} options Object with the following properties:
//      * @param {Object} [options.heatmapoptions] Optional heatmap.js options to be used (see http://www.patrick-wied.at/static/heatmapjs/docs.html#h337-create).
//      * @param {Object} [options.bounds] The bounding box for the heatmap in WGS84 coordinates.
//      * @param {Number} [options.bounds.north] The northernmost point of the heatmap.
//      * @param {Number} [options.bounds.south] The southernmost point of the heatmap.
//      * @param {Number} [options.bounds.west] The westernmost point of the heatmap.
//      * @param {Number} [options.bounds.east] The easternmost point of the heatmap.
//      * @param {Object} [options.data] Data to be used for the heatmap.
//      * @param {Object} [options.data.min] Minimum allowed point value.
//      * @param {Object} [options.data.max] Maximum allowed point value.
//      * @param {Array} [options.data.points] The data points for the heatmap containing x=lon, y=lat and value=number.
//      *
//      * @see HeatmapImageryProvider
//      * @see ArcGisMapServerImageryProvider
//      * @see BingMapsImageryProvider
//      * @see GoogleEarthImageryProvider
//      * @see OpenStreetMapImageryProvider
//      * @see TileMapServiceImageryProvider
//      * @see WebMapServiceImageryProvider
//      */
//     var HeatmapImageryProvider = function(options) {
//         options = defaultValue(options, {});
//         var bounds = options.bounds;
//         var data = options.data;

//         if (!defined(bounds)) {
//             throw new DeveloperError('options.bounds is required.');
//         } else if (!defined(bounds.north) || !defined(bounds.south) || !defined(bounds.east) || !defined(bounds.west)) {
//             throw new DeveloperError('options.bounds.north, options.bounds.south, options.bounds.east and options.bounds.west are required.');
//         }

//         if (!defined(data)) {
//             throw new DeveloperError('data is required.');
//         } else if (!defined(data.min) || !defined(data.max) || !defined(data.points)) {
//             throw new DeveloperError('options.bounds.north, bounds.south, bounds.east and bounds.west are required.');
//         }

//         this._wmp = new Cesium.WebMercatorProjection();
//         this._mbounds = this.wgs84ToMercatorBB(bounds);
//         this._options = defaultValue(options.heatmapoptions, {});
//         this._options.gradient = defaultValue(this._options.gradient, { 0.25: "rgb(0,0,255)", 0.55: "rgb(0,255,0)", 0.85: "yellow", 1.0: "rgb(255,0,0)"});

//         this._setWidthAndHeight(this._mbounds);
//         this._options.radius = Math.round(defaultValue(this._options.radius, ((this.width > this.height) ? this.width / 60 : this.height / 60)));

//         this._spacing = this._options.radius * 1.5;
//         this._xoffset = this._mbounds.west;
//         this._yoffset = this._mbounds.south;

//         this.width = Math.round(this.width + this._spacing * 2);
//         this.height = Math.round(this.height + this._spacing * 2);

//         this._mbounds.west -= this._spacing * this._factor;
//         this._mbounds.east += this._spacing * this._factor;
//         this._mbounds.south -= this._spacing * this._factor;
//         this._mbounds.north += this._spacing * this._factor;

//         this.bounds = this.mercatorToWgs84BB(this._mbounds);

//         this._container = this._getContainer(this.width, this.height);
//         this._options.container = this._container;
//         this._heatmap = h337.create(this._options);
//         this._canvas = this._container.children[0];

//         this._tilingScheme = new Cesium.WebMercatorTilingScheme({
//             rectangleSouthwestInMeters: new Cesium.Cartesian2(this._mbounds.west, this._mbounds.south),
//             rectangleNortheastInMeters: new Cesium.Cartesian2(this._mbounds.east, this._mbounds.north)
//         });

//         this._image = this._canvas;
//         this._texture = undefined;
//         this._tileWidth = this.width;
//         this._tileHeight = this.height;
//         this._ready = false;

//         if (options.data) {
//             this._ready = this.setWGS84Data(options.data.min, options.data.max, options.data.points);
//         }
//     };

//     defineProperties(HeatmapImageryProvider.prototype, {
//         /**
//          * Gets the URL of the single, top-level imagery tile.
//          * @memberof HeatmapImageryProvider.prototype
//          * @type {String}
//          * @readonly
//          */
//         url : {
//             get : function() {
//                 return this._url;
//             }
//         },

//         /**
//          * Gets the width of each tile, in pixels. This function should
//          * not be called before {@link HeatmapImageryProvider#ready} returns true.
//          * @memberof HeatmapImageryProvider.prototype
//          * @type {Number}
//          * @readonly
//          */
//         tileWidth : {
//             get : function() {
//                 if (!this._ready) {
//                     throw new DeveloperError('tileWidth must not be called before the imagery provider is ready.');
//                 }

//                 return this._tileWidth;
//             }
//         },

//         /**
//          * Gets the height of each tile, in pixels.  This function should
//          * not be called before {@link HeatmapImageryProvider#ready} returns true.
//          * @memberof HeatmapImageryProvider.prototype
//          * @type {Number}
//          * @readonly
//          */
//         tileHeight: {
//             get : function() {
//                 if (!this._ready) {
//                     throw new DeveloperError('tileHeight must not be called before the imagery provider is ready.');
//                 }

//                 return this._tileHeight;
//             }
//         },

//         /**
//          * Gets the maximum level-of-detail that can be requested.  This function should
//          * not be called before {@link HeatmapImageryProvider#ready} returns true.
//          * @memberof HeatmapImageryProvider.prototype
//          * @type {Number}
//          * @readonly
//          */
//         maximumLevel : {
//             get : function() {
//                 if (!this._ready) {
//                     throw new DeveloperError('maximumLevel must not be called before the imagery provider is ready.');
//                 }

//                 return 0;
//             }
//         },

//         /**
//          * Gets the minimum level-of-detail that can be requested.  This function should
//          * not be called before {@link HeatmapImageryProvider#ready} returns true.
//          * @memberof HeatmapImageryProvider.prototype
//          * @type {Number}
//          * @readonly
//          */
//         minimumLevel : {
//             get : function() {
//                 if (!this._ready) {
//                     throw new DeveloperError('minimumLevel must not be called before the imagery provider is ready.');
//                 }

//                 return 0;
//             }
//         },

//         /**
//          * Gets the tiling scheme used by this provider.  This function should
//          * not be called before {@link HeatmapImageryProvider#ready} returns true.
//          * @memberof HeatmapImageryProvider.prototype
//          * @type {TilingScheme}
//          * @readonly
//          */
//         tilingScheme : {
//             get : function() {
//                 if (!this._ready) {
//                     throw new DeveloperError('tilingScheme must not be called before the imagery provider is ready.');
//                 }

//                 return this._tilingScheme;
//             }
//         },

//         /**
//          * Gets the rectangle, in radians, of the imagery provided by this instance.  This function should
//          * not be called before {@link HeatmapImageryProvider#ready} returns true.
//          * @memberof HeatmapImageryProvider.prototype
//          * @type {Rectangle}
//          * @readonly
//          */
//         rectangle : {
//             get : function() {
//                 return this._tilingScheme.rectangle;//TODO: change to custom rectangle?
//             }
//         },

//         /**
//          * Gets the tile discard policy.  If not undefined, the discard policy is responsible
//          * for filtering out "missing" tiles via its shouldDiscardImage function.  If this function
//          * returns undefined, no tiles are filtered.  This function should
//          * not be called before {@link HeatmapImageryProvider#ready} returns true.
//          * @memberof HeatmapImageryProvider.prototype
//          * @type {TileDiscardPolicy}
//          * @readonly
//          */
//         tileDiscardPolicy : {
//             get : function() {
//                 if (!this._ready) {
//                     throw new DeveloperError('tileDiscardPolicy must not be called before the imagery provider is ready.');
//                 }

//                 return undefined;
//             }
//         },

//         /**
//          * Gets an event that is raised when the imagery provider encounters an asynchronous error.  By subscribing
//          * to the event, you will be notified of the error and can potentially recover from it.  Event listeners
//          * are passed an instance of {@link TileProviderError}.
//          * @memberof HeatmapImageryProvider.prototype
//          * @type {Event}
//          * @readonly
//          */
//         errorEvent : {
//             get : function() {
//                 return this._errorEvent;
//             }
//         },

//         /**
//          * Gets a value indicating whether or not the provider is ready for use.
//          * @memberof HeatmapImageryProvider.prototype
//          * @type {Boolean}
//          * @readonly
//          */
//         ready : {
//             get : function() {
//                 return this._ready;
//             }
//         },

//         /**
//          * Gets the credit to display when this imagery provider is active.  Typically this is used to credit
//          * the source of the imagery.  This function should not be called before {@link HeatmapImageryProvider#ready} returns true.
//          * @memberof HeatmapImageryProvider.prototype
//          * @type {Credit}
//          * @readonly
//          */
//         credit : {
//             get : function() {
//                 return this._credit;
//             }
//         },

//         /**
//          * Gets a value indicating whether or not the images provided by this imagery provider
//          * include an alpha channel.  If this property is false, an alpha channel, if present, will
//          * be ignored.  If this property is true, any images without an alpha channel will be treated
//          * as if their alpha is 1.0 everywhere.  When this property is false, memory usage
//          * and texture upload time are reduced.
//          * @memberof HeatmapImageryProvider.prototype
//          * @type {Boolean}
//          * @readonly
//          */
//         hasAlphaChannel : {
//             get : function() {
//                 return true;
//             }
//         }
//     });

//     HeatmapImageryProvider.prototype._setWidthAndHeight = function(mbb) {
//         var maxCanvasSize = 2000;
//         var minCanvasSize = 700;
//         this.width = ((mbb.east > 0 && mbb.west < 0) ? mbb.east + Math.abs(mbb.west) : Math.abs(mbb.east - mbb.west));
//         this.height = ((mbb.north > 0 && mbb.south < 0) ? mbb.north + Math.abs(mbb.south) : Math.abs(mbb.north - mbb.south));
//         this._factor = 1;

//         if (this.width > this.height && this.width > maxCanvasSize) {
//             this._factor = this.width / maxCanvasSize;

//             if (this.height / this._factor < minCanvasSize) {
//                 this._factor = this.height / minCanvasSize;
//             }
//         } else if (this.height > this.width && this.height > maxCanvasSize) {
//             this._factor = this.height / maxCanvasSize;

//             if (this.width / this._factor < minCanvasSize) {
//                 this._factor = this.width / minCanvasSize;
//             }
//         } else if (this.width < this.height && this.width < minCanvasSize) {
//             this._factor = this.width / minCanvasSize;

//             if (this.height / this._factor > maxCanvasSize) {
//                 this._factor = this.height / maxCanvasSize;
//             }
//         } else if (this.height < this.width && this.height < minCanvasSize) {
//             this._factor = this.height / minCanvasSize;

//             if (this.width / this._factor > maxCanvasSize) {
//                 this._factor = this.width / maxCanvasSize;
//             }
//         }

//         this.width = this.width / this._factor;
//         this.height = this.height / this._factor;
//     };

//     HeatmapImageryProvider.prototype._getContainer = function(width, height, id) {
//         var c = document.createElement("div");
//         if (id) { c.setAttribute("id", id); }
//         c.setAttribute("style", "width: " + width + "px; height: " + height + "px; margin: 0px; display: none;");
//         document.body.appendChild(c);
//         return c;
//     };

//     /**
//      * Convert a WGS84 location into a Mercator location.
//      *
//      * @param {Object} point The WGS84 location.
//      * @param {Number} [point.x] The longitude of the location.
//      * @param {Number} [point.y] The latitude of the location.
//      * @returns {Cesium.Cartesian3} The Mercator location.
//      */
//     HeatmapImageryProvider.prototype.wgs84ToMercator = function(point) {
//         return this._wmp.project(Cesium.Cartographic.fromDegrees(point.x, point.y));
//     };

//     /**
//      * Convert a WGS84 bounding box into a Mercator bounding box.
//      *
//      * @param {Object} bounds The WGS84 bounding box.
//      * @param {Number} [bounds.north] The northernmost position.
//      * @param {Number} [bounds.south] The southrnmost position.
//      * @param {Number} [bounds.east] The easternmost position.
//      * @param {Number} [bounds.west] The westernmost position.
//      * @returns {Object} The Mercator bounding box containing north, south, east and west properties.
//      */
//     HeatmapImageryProvider.prototype.wgs84ToMercatorBB = function(bounds) {
//         var ne = this._wmp.project(Cesium.Cartographic.fromDegrees(bounds.east, bounds.north));
//         var sw = this._wmp.project(Cesium.Cartographic.fromDegrees(bounds.west, bounds.south));
//         return {
//             north: ne.y,
//             south: sw.y,
//             east: ne.x,
//             west: sw.x
//         };
//     };

//     /**
//      * Convert a mercator location into a WGS84 location.
//      *
//      * @param {Object} point The Mercator lcation.
//      * @param {Number} [point.x] The x of the location.
//      * @param {Number} [point.y] The y of the location.
//      * @returns {Object} The WGS84 location.
//      */
//     HeatmapImageryProvider.prototype.mercatorToWgs84 = function(p) {
//         var wp = this._wmp.unproject(new Cesium.Cartesian3(p.x, p.y));
//         return {
//             x: wp.longitude,
//             y: wp.latitude
//         };
//     };

//     /**
//      * Convert a Mercator bounding box into a WGS84 bounding box.
//      *
//      * @param {Object} bounds The Mercator bounding box.
//      * @param {Number} [bounds.north] The northernmost position.
//      * @param {Number} [bounds.south] The southrnmost position.
//      * @param {Number} [bounds.east] The easternmost position.
//      * @param {Number} [bounds.west] The westernmost position.
//      * @returns {Object} The WGS84 bounding box containing north, south, east and west properties.
//      */
//     HeatmapImageryProvider.prototype.mercatorToWgs84BB = function(bounds) {
//         var sw = this._wmp.unproject(new Cesium.Cartesian3(bounds.west, bounds.south));
//         var ne = this._wmp.unproject(new Cesium.Cartesian3(bounds.east, bounds.north));
//         return {
//             north: this.rad2deg(ne.latitude),
//             east: this.rad2deg(ne.longitude),
//             south: this.rad2deg(sw.latitude),
//             west: this.rad2deg(sw.longitude)
//         };
//     };

//     /**
//      * Convert degrees into radians.
//      *
//      * @param {Number} degrees The degrees to be converted to radians.
//      * @returns {Number} The converted radians.
//      */
//     HeatmapImageryProvider.prototype.deg2rad = function(degrees) {
//         return (degrees * (Math.PI / 180.0));
//     };

//     /**
//      * Convert radians into degrees.
//      *
//      * @param {Number} radians The radians to be converted to degrees.
//      * @returns {Number} The converted degrees.
//      */
//     HeatmapImageryProvider.prototype.rad2deg = function(radians) {
//         return (radians / (Math.PI / 180.0));
//     };

//     /**
//      * Convert a WGS84 location to the corresponding heatmap location.
//      *
//      * @param {Object} point The WGS84 location.
//      * @param {Number} [point.x] The longitude of the location.
//      * @param {Number} [point.y] The latitude of the location.
//      * @returns {Object} The corresponding heatmap location.
//      */
//     HeatmapImageryProvider.prototype.wgs84PointToHeatmapPoint = function(point) {
//         return this.mercatorPointToHeatmapPoint(this.wgs84ToMercator(point));
//     };

//     /**
//      * Convert a mercator location to the corresponding heatmap location.
//      *
//      * @param {Object} point The Mercator lcation.
//      * @param {Number} [point.x] The x of the location.
//      * @param {Number} [point.y] The y of the location.
//      * @returns {Object} The corresponding heatmap location.
//      */
//     HeatmapImageryProvider.prototype.mercatorPointToHeatmapPoint = function(point) {
//         var pn = {};

//         pn.x = Math.round((point.x - this._xoffset) / this._factor + this._spacing);
//         pn.y = Math.round((point.y - this._yoffset) / this._factor + this._spacing);
//         pn.y = this.height - pn.y;

//         return pn;
//     };

//     /**
//      * Set an array of heatmap locations.
//      *
//      * @param {Number} min The minimum allowed value for the data points.
//      * @param {Number} max The maximum allowed value for the data points.
//      * @param {Array} data An array of data points with heatmap coordinates(x, y) and value
//      * @returns {Boolean} Wheter or not the data was successfully added or failed.
//      */
//     HeatmapImageryProvider.prototype.setData = function(min, max, data) {
//         if (data && data.length > 0 && min !== null && min !== false && max !== null && max !== false) {
//             this._heatmap.setData({
//                 min: min,
//                 max: max,
//                 data: data
//             });

//             return true;
//         }

//         return false;
//     };

//     /**
//      * Set an array of WGS84 locations.
//      *
//      * @param {Number} min The minimum allowed value for the data points.
//      * @param {Number} max The maximum allowed value for the data points.
//      * @param {Array} data An array of data points with WGS84 coordinates(x=lon, y=lat) and value
//      * @returns {Boolean} Wheter or not the data was successfully added or failed.
//      */
//     HeatmapImageryProvider.prototype.setWGS84Data = function(min, max, data) {
//         if (data && data.length > 0 && min !== null && min !== false && max !== null && max !== false) {
//             var convdata = [];

//             for (var i = 0; i < data.length; i++) {
//                 var gp = data[i];

//                 var hp = this.wgs84PointToHeatmapPoint(gp);
//                 if (gp.value || gp.value === 0) { hp.value = gp.value; }

//                 convdata.push(hp);
//             }

//             return this.setData(min, max, convdata);
//         }

//         return false;
//     };

//     /**
//      * Gets the credits to be displayed when a given tile is displayed.
//      *
//      * @param {Number} x The tile X coordinate.
//      * @param {Number} y The tile Y coordinate.
//      * @param {Number} level The tile level;
//      * @returns {Credit[]} The credits to be displayed when the tile is displayed.
//      *
//      * @exception {DeveloperError} <code>getTileCredits</code> must not be called before the imagery provider is ready.
//      */
//     HeatmapImageryProvider.prototype.getTileCredits = function(x, y, level) {
//         return undefined;
//     };

//     /**
//      * Requests the image for a given tile.  This function should
//      * not be called before {@link HeatmapImageryProvider#ready} returns true.
//      *
//      * @param {Number} x The tile X coordinate.
//      * @param {Number} y The tile Y coordinate.
//      * @param {Number} level The tile level.
//      * @returns {Promise} A promise for the image that will resolve when the image is available, or
//      *          undefined if there are too many active requests to the server, and the request
//      *          should be retried later.  The resolved image may be either an
//      *          Image or a Canvas DOM object.
//      *
//      * @exception {DeveloperError} <code>requestImage</code> must not be called before the imagery provider is ready.
//      */
//     HeatmapImageryProvider.prototype.requestImage = function(x, y, level) {
//         if (!this._ready) {
//             throw new DeveloperError('requestImage must not be called before the imagery provider is ready.');
//         }

//         return this._image;
//     };

//     /**
//      * Picking features is not currently supported by this imagery provider, so this function simply returns
//      * undefined.
//      *
//      * @param {Number} x The tile X coordinate.
//      * @param {Number} y The tile Y coordinate.
//      * @param {Number} level The tile level.
//      * @param {Number} longitude The longitude at which to pick features.
//      * @param {Number} latitude  The latitude at which to pick features.
//      * @return {Promise} A promise for the picked features that will resolve when the asynchronous
//      *                   picking completes.  The resolved value is an array of {@link ImageryLayerFeatureInfo}
//      *                   instances.  The array may be empty if no features are found at the given location.
//      *                   It may also be undefined if picking is not supported.
//      */
//     HeatmapImageryProvider.prototype.pickFeatures = function() {
//         return undefined;
//     };

//     return HeatmapImageryProvider;
// });

/*  DON'T TOUCH:
 *
 *  heatmap.js v2.0.0 | JavaScript Heatmap Library: http://www.patrick-wied.at/static/heatmapjs/
 *
 *  Copyright 2008-2014 Patrick Wied <heatmapjs@patrick-wied.at> - All rights reserved.
 *  Dual licensed under MIT and Beerware license 
 *
 *  :: 2014-10-31 21:16
 */
(function(a, b, c) { if (typeof module !== "undefined" && module.exports) { module.exports = c() } else if (typeof define === "function" && define.amd) { define(c) } else { b[a] = c() } })("h337", this, function() { var a = { defaultRadius: 40, defaultRenderer: "canvas2d", defaultGradient: { .25: "rgb(0,0,255)", .55: "rgb(0,255,0)", .85: "yellow", 1: "rgb(255,0,0)" }, defaultMaxOpacity: 1, defaultMinOpacity: 0, defaultBlur: .85, defaultXField: "x", defaultYField: "y", defaultValueField: "value", plugins: {} }; var b = function h() { var b = function d(a) { this._coordinator = {};
            this._data = [];
            this._radi = [];
            this._min = 0;
            this._max = 1;
            this._xField = a["xField"] || a.defaultXField;
            this._yField = a["yField"] || a.defaultYField;
            this._valueField = a["valueField"] || a.defaultValueField; if (a["radius"]) { this._cfgRadius = a["radius"] } }; var c = a.defaultRadius;
        b.prototype = { _organiseData: function(a, b) { var d = a[this._xField]; var e = a[this._yField]; var f = this._radi; var g = this._data; var h = this._max; var i = this._min; var j = a[this._valueField] || 1; var k = a.radius || this._cfgRadius || c; if (!g[d]) { g[d] = [];
                    f[d] = [] } if (!g[d][e]) { g[d][e] = j;
                    f[d][e] = k } else { g[d][e] += j } if (g[d][e] > h) { if (!b) { this._max = g[d][e] } else { this.setDataMax(g[d][e]) } return false } else { return { x: d, y: e, value: j, radius: k, min: i, max: h } } }, _unOrganizeData: function() { var a = []; var b = this._data; var c = this._radi; for (var d in b) { for (var e in b[d]) { a.push({ x: d, y: e, radius: c[d][e], value: b[d][e] }) } } return { min: this._min, max: this._max, data: a } }, _onExtremaChange: function() { this._coordinator.emit("extremachange", { min: this._min, max: this._max }) }, addData: function() { if (arguments[0].length > 0) { var a = arguments[0]; var b = a.length; while (b--) { this.addData.call(this, a[b]) } } else { var c = this._organiseData(arguments[0], true); if (c) { this._coordinator.emit("renderpartial", { min: this._min, max: this._max, data: [c] }) } } return this }, setData: function(a) { var b = a.data; var c = b.length;
                this._data = [];
                this._radi = []; for (var d = 0; d < c; d++) { this._organiseData(b[d], false) }
                this._max = a.max;
                this._min = a.min || 0;
                this._onExtremaChange();
                this._coordinator.emit("renderall", this._getInternalData()); return this }, removeData: function() {}, setDataMax: function(a) { this._max = a;
                this._onExtremaChange();
                this._coordinator.emit("renderall", this._getInternalData()); return this }, setDataMin: function(a) { this._min = a;
                this._onExtremaChange();
                this._coordinator.emit("renderall", this._getInternalData()); return this }, setCoordinator: function(a) { this._coordinator = a }, _getInternalData: function() { return { max: this._max, min: this._min, data: this._data, radi: this._radi } }, getData: function() { return this._unOrganizeData() } }; return b }(); var c = function i() { var a = function(a) { var b = a.gradient || a.defaultGradient; var c = document.createElement("canvas"); var d = c.getContext("2d");
            c.width = 256;
            c.height = 1; var e = d.createLinearGradient(0, 0, 256, 1); for (var f in b) { e.addColorStop(f, b[f]) }
            d.fillStyle = e;
            d.fillRect(0, 0, 256, 1); return d.getImageData(0, 0, 256, 1).data }; var b = function(a, b) { var c = document.createElement("canvas"); var d = c.getContext("2d"); var e = a; var f = a;
            c.width = c.height = a * 2; if (b == 1) { d.beginPath();
                d.arc(e, f, a, 0, 2 * Math.PI, false);
                d.fillStyle = "rgba(0,0,0,1)";
                d.fill() } else { var g = d.createRadialGradient(e, f, a * b, e, f, a);
                g.addColorStop(0, "rgba(0,0,0,1)");
                g.addColorStop(1, "rgba(0,0,0,0)");
                d.fillStyle = g;
                d.fillRect(0, 0, 2 * a, 2 * a) } return c }; var c = function(a) { var b = []; var c = a.min; var d = a.max; var e = a.radi; var a = a.data; var f = Object.keys(a); var g = f.length; while (g--) { var h = f[g]; var i = Object.keys(a[h]); var j = i.length; while (j--) { var k = i[j]; var l = a[h][k]; var m = e[h][k];
                    b.push({ x: h, y: k, value: l, radius: m }) } } return { min: c, max: d, data: b } };

        function d(b) { var c = b.container; var d = this.shadowCanvas = document.createElement("canvas"); var e = this.canvas = b.canvas || document.createElement("canvas"); var f = this._renderBoundaries = [1e4, 1e4, 0, 0]; var g = getComputedStyle(b.container) || {};
            e.className = "heatmap-canvas";
            this._width = e.width = d.width = +g.width.replace(/px/, "");
            this._height = e.height = d.height = +g.height.replace(/px/, "");
            this.shadowCtx = d.getContext("2d");
            this.ctx = e.getContext("2d");
            e.style.cssText = d.style.cssText = "position:absolute;left:0;top:0;";
            c.style.position = "relative";
            c.appendChild(e);
            this._palette = a(b);
            this._templates = {};
            this._setStyles(b) }
        d.prototype = { renderPartial: function(a) { this._drawAlpha(a);
                this._colorize() }, renderAll: function(a) { this._clear();
                this._drawAlpha(c(a));
                this._colorize() }, _updateGradient: function(b) { this._palette = a(b) }, updateConfig: function(a) { if (a["gradient"]) { this._updateGradient(a) }
                this._setStyles(a) }, setDimensions: function(a, b) { this._width = a;
                this._height = b;
                this.canvas.width = this.shadowCanvas.width = a;
                this.canvas.height = this.shadowCanvas.height = b }, _clear: function() { this.shadowCtx.clearRect(0, 0, this._width, this._height);
                this.ctx.clearRect(0, 0, this._width, this._height) }, _setStyles: function(a) { this._blur = a.blur == 0 ? 0 : a.blur || a.defaultBlur; if (a.backgroundColor) { this.canvas.style.backgroundColor = a.backgroundColor }
                this._opacity = (a.opacity || 0) * 255;
                this._maxOpacity = (a.maxOpacity || a.defaultMaxOpacity) * 255;
                this._minOpacity = (a.minOpacity || a.defaultMinOpacity) * 255;
                this._useGradientOpacity = !!a.useGradientOpacity }, _drawAlpha: function(a) { var c = this._min = a.min; var d = this._max = a.max; var a = a.data || []; var e = a.length; var f = 1 - this._blur; while (e--) { var g = a[e]; var h = g.x; var i = g.y; var j = g.radius; var k = Math.min(g.value, d); var l = h - j; var m = i - j; var n = this.shadowCtx; var o; if (!this._templates[j]) { this._templates[j] = o = b(j, f) } else { o = this._templates[j] }
                    n.globalAlpha = (k - c) / (d - c);
                    n.drawImage(o, l, m); if (l < this._renderBoundaries[0]) { this._renderBoundaries[0] = l } if (m < this._renderBoundaries[1]) { this._renderBoundaries[1] = m } if (l + 2 * j > this._renderBoundaries[2]) { this._renderBoundaries[2] = l + 2 * j } if (m + 2 * j > this._renderBoundaries[3]) { this._renderBoundaries[3] = m + 2 * j } } }, _colorize: function() { var a = this._renderBoundaries[0]; var b = this._renderBoundaries[1]; var c = this._renderBoundaries[2] - a; var d = this._renderBoundaries[3] - b; var e = this._width; var f = this._height; var g = this._opacity; var h = this._maxOpacity; var i = this._minOpacity; var j = this._useGradientOpacity; if (a < 0) { a = 0 } if (b < 0) { b = 0 } if (a + c > e) { c = e - a } if (b + d > f) { d = f - b } var k = this.shadowCtx.getImageData(a, b, c, d); var l = k.data; var m = l.length; var n = this._palette; for (var o = 3; o < m; o += 4) { var p = l[o]; var q = p * 4; if (!q) { continue } var r; if (g > 0) { r = g } else { if (p < h) { if (p < i) { r = i } else { r = p } } else { r = h } }
                    l[o - 3] = n[q];
                    l[o - 2] = n[q + 1];
                    l[o - 1] = n[q + 2];
                    l[o] = j ? n[q + 3] : r }
                k.data = l;
                this.ctx.putImageData(k, a, b);
                this._renderBoundaries = [1e3, 1e3, 0, 0] }, getValueAt: function(a) { var b; var c = this.shadowCtx; var d = c.getImageData(a.x, a.y, 1, 1); var e = d.data[3]; var f = this._max; var g = this._min;
                b = Math.abs(f - g) * (e / 255) >> 0; return b }, getDataURL: function() { return this.canvas.toDataURL() } }; return d }(); var d = function j() { var b = false; if (a["defaultRenderer"] === "canvas2d") { b = c } return b }(); var e = { merge: function() { var a = {}; var b = arguments.length; for (var c = 0; c < b; c++) { var d = arguments[c]; for (var e in d) { a[e] = d[e] } } return a } }; var f = function k() { var c = function h() {
            function a() { this.cStore = {} }
            a.prototype = { on: function(a, b, c) { var d = this.cStore; if (!d[a]) { d[a] = [] }
                    d[a].push(function(a) { return b.call(c, a) }) }, emit: function(a, b) { var c = this.cStore; if (c[a]) { var d = c[a].length; for (var e = 0; e < d; e++) { var f = c[a][e];
                            f(b) } } } }; return a }(); var f = function(a) { var b = a._renderer; var c = a._coordinator; var d = a._store;
            c.on("renderpartial", b.renderPartial, b);
            c.on("renderall", b.renderAll, b);
            c.on("extremachange", function(b) { a._config.onExtremaChange && a._config.onExtremaChange({ min: b.min, max: b.max, gradient: a._config["gradient"] || a._config["defaultGradient"] }) });
            d.setCoordinator(c) };

        function g() { var g = this._config = e.merge(a, arguments[0] || {});
            this._coordinator = new c; if (g["plugin"]) { var h = g["plugin"]; if (!a.plugins[h]) { throw new Error("Plugin '" + h + "' not found. Maybe it was not registered.") } else { var i = a.plugins[h];
                    this._renderer = new i.renderer(g);
                    this._store = new i.store(g) } } else { this._renderer = new d(g);
                this._store = new b(g) }
            f(this) }
        g.prototype = { addData: function() { this._store.addData.apply(this._store, arguments); return this }, removeData: function() { this._store.removeData && this._store.removeData.apply(this._store, arguments); return this }, setData: function() { this._store.setData.apply(this._store, arguments); return this }, setDataMax: function() { this._store.setDataMax.apply(this._store, arguments); return this }, setDataMin: function() { this._store.setDataMin.apply(this._store, arguments); return this }, configure: function(a) { this._config = e.merge(this._config, a);
                this._renderer.updateConfig(this._config);
                this._coordinator.emit("renderall", this._store._getInternalData()); return this }, repaint: function() { this._coordinator.emit("renderall", this._store._getInternalData()); return this }, getData: function() { return this._store.getData() }, getDataURL: function() { return this._renderer.getDataURL() }, getValueAt: function(a) { if (this._store.getValueAt) { return this._store.getValueAt(a) } else if (this._renderer.getValueAt) { return this._renderer.getValueAt(a) } else { return null } } }; return g }(); var g = { create: function(a) { return new f(a) }, register: function(b, c) { a.plugins[b] = c } }; return g });;
///<jscompress sourcefile="VFGImgProvider.js" />
VFG.Provider=function(){}
VFG.Provider.Map=new Map();
VFG.Provider.hasTerrain=false;
VFG.Provider.createUrlTemplateImageryProvider = function (ops) {
	return new Cesium.UrlTemplateImageryProvider(ops);
};

/**
 * WebMapTile
 * @param {Object} ops
 */
VFG.Provider.createWebMapTileServiceImageryProvider = function (ops) {
	return new Cesium.WebMapTileServiceImageryProvider(ops);
};

/**
 * BingMaps
 * @param {Object} ops
 */
VFG.Provider.createBingMapsImageryProvider = function (ops) {
	return new Cesium.BingMapsImageryProvider(ops);
};

/**
 * BingMapsGeocoderService
 * @param {Object} ops
 */
VFG.Provider.createBingMapsGeocoderService = function (ops) {
	return new Cesium.BingMapsGeocoderService(ops);
};

/**
 * ArcGisMap
 * @param {Object} ops
 */
VFG.Provider.createArcGisMapServerImageryProvider = function (ops) {
	return new Cesium.ArcGisMapServerImageryProvider(ops);
};

/**
 * ArcGISTiledElevationTerrain
 * @param {Object} ops
 */
VFG.Provider.createArcGISTiledElevationTerrainProvider = function (ops) {
	return new Cesium.ArcGISTiledElevationTerrainProvider(ops);
};

/**
 * OpenStreetMapImageryProvider
 * @param {Object} ops
 */
VFG.Provider.createOpenStreetMapImageryProvider = function (ops) {
	return new Cesium.OpenStreetMapImageryProvider(ops);
};

/**
 * SingleTileImageryProvider
 * @param {Object} ops
 */
VFG.Provider.createSingleTileImageryProvider = function (ops) {
	return new Cesium.SingleTileImageryProvider(ops);
};

/**
 * TileMapServiceImageryProvider
 * @param {Object} ops
 */
VFG.Provider.createTileMapServiceImageryProvider = function (ops) {
	return new Cesium.TileMapServiceImageryProvider(ops);
};

/**
 * WebMapServiceImageryProvider
 * @param {Object} ops
 */
VFG.Provider.createWebMapServiceImageryProvider = function (ops) {
	return new Cesium.WebMapServiceImageryProvider(ops);
};

/**
 * CesiumTerrainProvider
 * @param {Object} ops
 */
VFG.Provider.createTerrainProvider = function (ops) {
	return new Cesium.CesiumTerrainProvider(ops);
};

/**
 * 官网世界地形
 */
VFG.Provider.createWorldTerrainProvider = function () {
	return new Cesium.createWorldTerrain();
};


/**
 * 获取图层集合
 */
VFG.Provider.getImageryLayers  = function (viewer) {
	return viewer.imageryLayers;
};


/**
 * 是否包含影像
 * @param {Object} layer
 */
VFG.Provider.containsImageryProvider  = function (viewer,layer) {
	 return viewer.imageryLayers.contains(layer);
};

/**
 * 序号获取影像
 * @param {Object} index
 */
VFG.Provider.getImageryProvider  = function (viewer,index) {
	 return viewer.imageryLayers.get(layer);
};

/**
 * 获取图层索引
 * @param {Object} layer
 */
VFG.Provider.indexOfImageryProvider  = function (viewer,layer) {
	 return viewer.imageryLayers.indexOf(layer);
};

/**
 * 清空图层
 * @param {Object} destroy
 */
VFG.Provider.removeAllImageryProviders  = function (viewer,destroy) {
	 return viewer.imageryLayers.removeAll(destroy);
};



/**
 * 至顶
 * @param {Object} layer
 */
VFG.Provider.raiseToTopImageryProviders  = function (viewer,layer) {
	 return viewer.imageryLayers.raiseToTop(layer);
};

/**
 * 上移
 * @param {Object} layer
 */
VFG.Provider.raiseImageryProviders  = function (viewer,layer) {
	 return viewer.imageryLayers.raise(layer);
};

/**
 * 下移
 * @param {Object} layer
 */
VFG.Provider.lowerImageryProviders  = function (viewer,layer) {
	 return viewer.imageryLayers.lower(layer);
};

/**
 * 至底
 * @param {Object} layer
 */
VFG.Provider.lowerToBottomImageryProviders  = function (viewer,layer) {
	 return viewer.imageryLayers.lowerToBottom(layer);
};

/**
 * 获取地形集合
 * @param {Object} ops
 * @param {Object} index
 */
VFG.Provider.getTerrainLayers  = function (viewer) {
	 return viewer.terrainLayers;
};

/**
 * 设置地形
 * @param {Object} terrainLayer
 */
VFG.Provider.addTerrainProvider  = function (viewer,terrainLayer) {
	 viewer.terrainProvider=terrainLayer;
};

/**
 * 移除地形
 * @param {Object} terrainLayer
 */
VFG.Provider.removeTerrainProvider  = function (viewer,terrainLayer) {
   viewer.terrainProvider = new Cesium.EllipsoidTerrainProvider({});
};

VFG.Provider.removeTerrainProvider  = function (viewer,terrainLayer) {
	viewer.terrainProvider = new Cesium.EllipsoidTerrainProvider({});
};


/**
 * 添加图层
 * @param {Object} ops
 */
VFG.Provider.addImageryProvider  = function (viewer,ops) {
	viewer.imageryLayers.addImageryProvider(ops);
};



VFG.Provider.addImageryProvider  = function (viewer,ops,index) {
	 viewer.imageryLayers.addImageryProvider(ops,index);
};

/**
 * 解析添加
 */
VFG.Provider.addImageryProvidersFromServ  = function (viewer,imglayers) {
	for(var i=0;i<imglayers.length;i++){
		var imglayer=imglayers[i];
		if(!this.Map.has(imglayer.id) && imglayer.show=='1'){
			if('terrain'==imglayer.dataType  ){
				var terrainProvider=VFG.Provider.getTerrainProviderFromServ(imglayer);
				if(terrainProvider){
					 this.hasTerrain=true;
					viewer.terrainProvider=terrainProvider;
					this.Map.set(imglayer.id,terrainProvider);
				}
			}else{
				var imageryProvider=this.getImageryProviderFromServ(imglayer);
				if(imageryProvider){
					var sImgPro=viewer.imageryLayers.addImageryProvider(imageryProvider);
					this.Map.set(imglayer.id,sImgPro);
				}
			}

		}
	}
};

VFG.Provider.addImageryProviderFromServ  = function (viewer,imglayer) {
	if(!this.Map.has(imglayer.id)){
		var imageryProvider=this.getImageryProviderFromServ(imglayer);
		if(imageryProvider){
			var sImgPro=viewer.imageryLayers.addImageryProvider(imageryProvider);
			this.Map.set(imglayer.id,sImgPro);
		}
	}
};

VFG.Provider.getImageryProviderFromServ  = function (imglayer) {
	if(imglayer.parameters){
		var parameter=eval('(' + imglayer.parameters + ')') ;
		if(parameter){
			if('URL'==imglayer.serverType){
				return this.createUrlTemplateImageryProvider(parameter);
			}
			else if('WMS'==imglayer.serverType){
				return new Cesium.WebMapServiceImageryProvider(parameter);
			}
			else if('WMTS'==imglayer.serverType){
				return new Cesium.WebMapTileServiceImageryProvider(parameter);
			}
			else if('ArcGis'==imglayer.serverType){
				return new Cesium.ArcGisMapServerImageryProvider(parameter);
			}
		}
	}
};

/**
 * 地形数据
 */
VFG.Provider.getTerrainProviderFromServ  = function (imglayer) {
	if(imglayer.parameters){
		var parameter=eval('(' + imglayer.parameters + ')') ;
		if(parameter){
			this.hasTerrain=true;
			return new Cesium.CesiumTerrainProvider(parameter)
		}
	}
};

/**
 * 移除图层
 * @param {Object} layer
 * @param {Object} destroy
 */
VFG.Provider.removeImageryProviders  = function (viewer,layer, destroy) {
	 return viewer.imageryLayers.remove(layer,destroy);
};

/**
 * 根据ID删除图层
 */
VFG.Provider.removeById  = function (viewer,id) {
	if(this.Map.has(id)){
		 viewer.imageryLayers.remove(this.Map.get(id),true);
		 this.Map.delete(id);
	}
};
VFG.Provider.removeTerrainProviderById  = function (viewer,id) {
	if(this.Map.has(id)){
		viewer.terrainProvider=new Cesium.EllipsoidTerrainProvider({});;
		 this.Map.delete(id);
		 this.hasTerrain=false;
	}
};


;
///<jscompress sourcefile="VFGRoadProvider.js" />
function VFGRoadProvider(viewer,options) {
  options = Cesium.defaultValue(options, Cesium.defaultValue.EMPTY_OBJECT);

  this._tilingScheme = Cesium.defined(options.tilingScheme) ? options.tilingScheme : new Cesium.GeographicTilingScheme({ ellipsoid: options.ellipsoid });
  this._cells = Cesium.defaultValue(options.cells, 8);
  this._color = Cesium.defaultValue(options.color, defaultColor);
  this._glowColor = Cesium.defaultValue(options.glowColor, defaultGlowColor);
  this._glowWidth = Cesium.defaultValue(options.glowWidth, 6);
  this._backgroundColor = Cesium.defaultValue(
    options.backgroundColor,
    defaultBackgroundColor
  );
  this._errorEvent = new Cesium.Event();

  this._tileWidth = Cesium.defaultValue(options.tileWidth, 256);
  this._tileHeight = Cesium.defaultValue(options.tileHeight, 256);

  // A little larger than tile size so lines are sharper
  // Note: can't be too much difference otherwise texture blowout
  this._canvasSize = Cesium.defaultValue(options.canvasSize, 256);

  // We only need a single canvas since all tiles will be the same
  this._canvas = this._createGridCanvas();
  this._readyPromise = Cesium.when.resolve(true);
  this._cacheMap=new Map();
  this._viewer=viewer;
  this._url=options.url;
  this._uri=options.uri;
  this._sceneId=options.sceneId;
  this._level = options.level ||11;
  this._layersId =VFG.Util.getUuid();
  this._layers=new Cesium.CustomDataSource(this._layersId);
  var _this=this;
  this._tileQueue = new  Cesium.Queue();
  this._cacheSize = 10;
}
VFGRoadProvider.prototype.pickFeatures = function (
  x,
  y,
  level,
  longitude,
  latitude
) {
  return undefined;
};
;
///<jscompress sourcefile="CesiumAxis.js" />
Cesium.DragControls = (function() {
	function _(viewer,options) {
        options =  Cesium.defaultValue(options, Cesium.defaultValue.EMPTY_OBJECT);
        this.viewer=viewer;
        /**
         * The length of the axes in meters.
         * @type {Number}
         * @default 10000000.0
         */
        this.length = Cesium.defaultValue(options.length, 10000000.0);
        this._length = undefined;

        /**
         * The width of the axes in pixels.
         * @type {Number}
         * @default 2.0
         */
        this.width =  Cesium.defaultValue(options.width, 2.0);
        this._width = undefined;

        /**
         * Determines if this primitive will be shown.
         * @type Boolean
         * @default true
         */
        this.show =  Cesium.defaultValue(options.show, true);

        /**
         * The 4x4 matrix that defines the reference frame, i.e., origin plus axes, to visualize.
         *
         * @type {Matrix4}
         * @default {@link Matrix4.IDENTITY}
         */
        
        
        this._rotate = options.rotate?options.rotate:{heading:0,pitch:0,roll:0};
        this._position = options.position;
       
        
        this.modelMatrix =  this.getModelMatrix();
        this._modelMatrix = new  Cesium.Matrix4();
        
        /**
         * User-defined value returned when the primitive is picked.
         *
         * @type {*}
         * @default undefined
         *
         * @see Scene#pick
         */
        this.id = options.id;
        this._id = undefined;
        this._primitive = undefined;
        this.scale;
        this.heading;
        this._init();
	}
	_.prototype._init = function() {
		var _self = this;
        this._primitiveX=new Cesium.Primitive({
	        geometryInstances : new  Cesium.GeometryInstance({
                geometry : new  Cesium.PolylineGeometry({
                    positions : [
                    	 Cesium.Cartesian3.ZERO,
                    	 Cesium.Cartesian3.UNIT_X
                    ],
                    width :16,
                    vertexFormat : Cesium.PolylineMaterialAppearance.VERTEX_FORMAT,
                    colors : [
                    	 Cesium.Color.RED,
                    	 Cesium.Color.RED
                    ],
                    arcType:  Cesium.ArcType.NONE
                }),
                id:_self.id+"-X",
                modelMatrix :  Cesium.Matrix4.multiplyByUniformScale(_self.modelMatrix,100, new Cesium.Matrix4()),
                pickPrimitive : this
            }),
            appearance : new Cesium.PolylineMaterialAppearance({
                material : new Cesium.Material({
                    fabric : {
                        type : 'PolylineArrow',
                        uniforms : {
                            color :  Cesium.Color.RED
                        }
                    }
                })
            })
	    })
        
	    this._primitiveY=new Cesium.Primitive({
	        geometryInstances : new  Cesium.GeometryInstance({
                geometry : new  Cesium.PolylineGeometry({
                    positions : [
                    	Cesium.Cartesian3.ZERO,
                    	Cesium.Cartesian3.UNIT_Y
                    ],
                    width :16,
                    vertexFormat : Cesium.PolylineMaterialAppearance.VERTEX_FORMAT,
                    colors : [
                    	 Cesium.Color.GREEN,
                    	 Cesium.Color.GREEN
                    ],
                    arcType:  Cesium.ArcType.NONE
                }),
                id:_self.id+"-Y",
                modelMatrix :  Cesium.Matrix4.multiplyByUniformScale(_self.modelMatrix,100, new Cesium.Matrix4()),
                pickPrimitive : this
            }),
            appearance : new Cesium.PolylineMaterialAppearance({
                material : new Cesium.Material({
                    fabric : {
                        type : 'PolylineArrow',
                        uniforms : {
                            color :  Cesium.Color.GREEN
                        }
                    }
                })
            })
	    })
        
	    this._primitiveZ=new Cesium.Primitive({
	        geometryInstances : new  Cesium.GeometryInstance({
                geometry : new  Cesium.PolylineGeometry({
                    positions : [
                    	 Cesium.Cartesian3.ZERO,
                    	 Cesium. Cartesian3.UNIT_Z
                    ],
                    width :16,
                    vertexFormat : Cesium.PolylineMaterialAppearance.VERTEX_FORMAT,
                    colors : [
                    	 Cesium.Color.BLUE,
                    	 Cesium.Color.BLUE
                    ],
                    arcType:  Cesium.ArcType.NONE
                }),
                id:_self.id+"-Z",
                modelMatrix :  Cesium.Matrix4.multiplyByUniformScale(_self.modelMatrix,100, new Cesium.Matrix4()),
                pickPrimitive : this
            }),
            appearance : new Cesium.PolylineMaterialAppearance({
                material : new Cesium.Material({
                    fabric : {
                        type : 'PolylineArrow',
                        uniforms : {
                            color :  Cesium.Color.BLUE
                        }
                    }
                })
            })
	    })
        
        this.viewer.scene.primitives.add( this._primitiveX );
        this.viewer.scene.primitives.add( this._primitiveY );
        this.viewer.scene.primitives.add( this._primitiveZ );
        
        var _this=this;
        var selectedAxis;
    	this._handler = new Cesium.ScreenSpaceEventHandler(this.viewer.scene.canvas);
    	
    	var startScrCartesian3;
    	
    	//鼠标左键按下
    	this._handler.setInputAction(function(e) {
    		var pick = _this.viewer.scene.pick(e.position);
    		if (Cesium.defined(pick) && pick.id && (  pick.id==_self.id+"-Z" ||   pick.id==_self.id+"-X" ||  pick.id==_self.id+"-Y"  )){
    			selectedAxis=pick;
    			startScrCartesian3=VFG.Util.getScreenToC3(_this.viewer,e.position);
    		 	if(selectedAxis.id==_self.id+"-X"){
    		 		_self._primitiveX.appearance.material.uniforms.color=Cesium.Color.YELLOW;
    		 		_self.viewer.scene.screenSpaceCameraController.enableRotate = false;//锁定相机
    		 	}
    		 	else if(selectedAxis.id==_self.id+"-Y"){
    		 		_self._primitiveY.appearance.material.uniforms.color=Cesium.Color.YELLOW
    		 		_self.viewer.scene.screenSpaceCameraController.enableRotate = false;//锁定相机
    		 	}
    		 	else if(selectedAxis.id==_self.id+"-Z"){
    		 		_self._primitiveZ.appearance.material.uniforms.color=Cesium.Color.YELLOW
    		 		_self.viewer.scene.screenSpaceCameraController.enableRotate = false;//锁定相机
    		 	}
    		}
		},Cesium.ScreenSpaceEventType.LEFT_DOWN);
    	
    	//鼠标左键释放
		this._handler.setInputAction(function(e) {
			if(selectedAxis){
    		 	if(selectedAxis.id==_self.id+"-X"){
    		 		_self._primitiveX.appearance.material.uniforms.color=Cesium.Color.RED;
    		 	}
    		 	else if(selectedAxis.id==_self.id+"-Y"){
    		 		_self._primitiveY.appearance.material.uniforms.color=Cesium.Color.GREEN
    		 	}
    		 	else if(selectedAxis.id==_self.id+"-Z"){
    		 		_self._primitiveZ.appearance.material.uniforms.color=Cesium.Color.BLUE
    		 	}
    		 	selectedAxis=null;
			}
	    	_self.viewer.scene.screenSpaceCameraController.enableRotate = true;//解锁相机
		},Cesium.ScreenSpaceEventType.LEFT_UP); 

    	this._handler.setInputAction(function(movement) {
    		if(selectedAxis){
/*    			var startScrCartesian3=VFG.Util.getScreenToC3(_this.viewer,movement.startPosition);
    			var endScrCartesian3=VFG.Util.getScreenToC3(_this.viewer,movement.endPosition);
    			
    			var startLnLa=VFG.Util.getC3ToLnLa(_this.viewer,startScrCartesian3);
				var endLnLa=VFG.Util.getC3ToLnLa(_this.viewer,endScrCartesian3);

				let AtoB = Cesium.Cartesian3.subtract(startScrCartesian3, endScrCartesian3, new Cesium.Cartesian3());
    			
    			var from = turf.point([startLnLa.x, startLnLa.y]);
    			var to = turf.point([endLnLa.x, endLnLa.y]);
    			var options = {units: 'kilometers'};
    			var distance = turf.distance(from, to, options)
    			console.log(AtoB);
    			*/
/*    			var endScrCartesian3=VFG.Util.getScreenToC3(_this.viewer,movement.endPosition);
    			var d=movement.startPosition.x-movement.endPosition.x;
    			console.log(d);*/
    			
    		//	console.log("start="+movement.startPosition.x," | end="+movement.endPosition.x);
    			
    			
    			var startScrCartesian3=VFG.Util.getScreenToC3(_this.viewer,movement.startPosition);
    			var endScrCartesian3=VFG.Util.getScreenToC3(_this.viewer,movement.endPosition);
    			
    			var startLnLa=VFG.Util.getC3ToLnLa(_this.viewer,startScrCartesian3);
				var endLnLa=VFG.Util.getC3ToLnLa(_this.viewer,endScrCartesian3);
    			
    			 var satrt = Cesium.Cartographic.fromDegrees(startLnLa.x, startLnLa.y)
    		     var end = Cesium.Cartographic.fromDegrees(endLnLa.x, endLnLa.y)
    		     var geodesic = new Cesium.EllipsoidGeodesic();
    		     geodesic.setEndPoints(satrt, end);
    		     var distance = geodesic.surfaceDistance
    			var cartesian3;
    			if(movement.endPosition.x>movement.startPosition.x){
    				console.log('右');
    				cartesian3=new Cesium.Cartesian3(-1*0.01,0,0)
    			}
    			if(movement.endPosition.x<movement.startPosition.x){
    				console.log('左');
    				cartesian3=new Cesium.Cartesian3(1*0.01,0,0)
    			}
				
				var translation=Cesium.Matrix4.fromTranslation(cartesian3);
    		    Cesium.Matrix4.multiply(_self._primitiveX.modelMatrix,translation,_self._primitiveX.modelMatrix);
    		    Cesium.Matrix4.multiply(_self._primitiveY.modelMatrix,translation,_self._primitiveY.modelMatrix);
    		    Cesium.Matrix4.multiply(_self._primitiveZ.modelMatrix,translation,_self._primitiveZ.modelMatrix);
    		    
    		    
    		    
    		    
    		}
		}, Cesium.ScreenSpaceEventType.MOUSE_MOVE);
		
       // document.onmousemove = _this.mousemove;  // 注册鼠标移动事件处理函数

        
	};
	_.prototype.mousemove = function(event) {
        event = this.handleEvent(event);
        o.style.left = ox + event.mx - mx  + "px";  // 定义拖动元素的x轴距离
        o.style.top = oy + event.my - my + "px";  // 定义拖动元素的y轴距离
	};
	_.prototype.handleEvent=function(event){  
        if( ! event){  // 兼容IE浏览器
            event = window.event;
            event.target = event.srcElement;
            event.layerX = event.offsetX;
            event.layerY = event.offsetY;
        }
        event.mx = event.pageX || event.clientX + document.body.scrollLeft;
        // 计算鼠标指针的x轴距离
        event.my = event.pageY || event.clientY + document.body.scrollTop;
        // 计算鼠标指针的y轴距离
        return event;  // 返回标准化的事件对象
    }
	_.prototype.getModelMatrix = function() {
		   var heading = Cesium.defaultValue(this._rotate.heading*1, 0.0);
		   var  pitch = Cesium.defaultValue(this._rotate.pitch*1, 0.0);
		   var  roll = Cesium.defaultValue(this._rotate.roll*1, 0.0);
	       var hpr = new Cesium.HeadingPitchRoll(heading, pitch, roll);
		   return Cesium.Transforms.headingPitchRollToFixedFrame(this._position, hpr, Cesium.Ellipsoid.WGS84);
	};
    /**
     * 销毁
     */
    _.prototype.destroy = function() {
        return Cesium.destroyObject(this); 
    };
	return _;
})();



;
///<jscompress sourcefile="CesiumDrag.js" />
/*  *  *  *  *  *  *  *  *  *  *
 *     绘制点
 *  *  *  *  *  *  *  *  *  *  */
!function(e, t) {
	"object" == typeof exports && "object" == typeof module ? module.exports = t(require("Cesium"))
			: "function" == typeof define && define.amd ? define([ "Cesium" ],
					t)
					: "object" == typeof exports ? exports.CesiumDrag = t(require("Cesium"))
							: e.CesiumDrag = t(e.Cesium)
}("undefined" != typeof self ? self : this, function(cesium) {
	function _(viewer, option) {
		this.viewer = viewer;
		this.option = option;
		if(!this.viewer){
			console.log('参数必填！！！');
			return;
		}
		this.cesiumTips=new Cesium.Tip(this.viewer);
		this.noPickEntity=option.primitive;
		this.dragType=option.type|| '';
		this.init();
	}
	_.prototype.init = function() {
		var _self = this;
		var pointDraged;
		var leftDownFlag=false;
		var startPoint;
		var polylinePreviousCoordinates;
		_self.handler = new Cesium.ScreenSpaceEventHandler(this.viewer.scene.canvas);
		
		//拾取实体
	    _self.handler.setInputAction(function (movement) {
            pointDraged = _self.viewer.scene.pick(movement.position);
            leftDownFlag = true;
            if(_self.dragType){
                if (pointDraged && pointDraged.id && pointDraged.id.type && pointDraged.id.type== _self.dragType) {
                    startPoint = _self.viewer.scene.pickPosition(movement.position);
                    _self.viewer.scene.screenSpaceCameraController.enableRotate = false;//锁定相机
                    if(_self.option.LEFT_DOWN){
                    	_self.option.LEFT_DOWN(movement,pointDraged);
                    }
                }
            }else{
                if (pointDraged) {
                    startPoint = _self.viewer.scene.pickPosition(movement.position);
                    _self.viewer.scene.screenSpaceCameraController.enableRotate = false;//锁定相机
                }	
            }
        }, Cesium.ScreenSpaceEventType.LEFT_DOWN);
	    
	    _self.handler.setInputAction(function (movement) {
            if(_self.option.LEFT_CLICK){
            	_self.option.LEFT_CLICK(movement);
            }
	    },Cesium.ScreenSpaceEventType.LEFT_CLICK)
	    
	    _self.handler.setInputAction(function (movement) {
            var clickEntiy =  _self.viewer.scene.pick(movement.position);
            if(clickEntiy && clickEntiy.id && clickEntiy.id.id){
                if(_self.option.MIDDLE_CLICK){
                	_self.option.MIDDLE_CLICK(clickEntiy.id.id,clickEntiy);
                }
            }
	    },Cesium.ScreenSpaceEventType.MIDDLE_CLICK)	    
	    
	    _self.handler.setInputAction(function (movement) {
            var clickEntiy =  _self.viewer.scene.pick(movement.position);
            if(clickEntiy && clickEntiy.id && clickEntiy.id.id){
                if(_self.option.LEFT_DOUBLE_CLICK){
                	_self.option.LEFT_DOUBLE_CLICK(clickEntiy.id.id,clickEntiy);
                }
            }
	    },Cesium.ScreenSpaceEventType.LEFT_DOUBLE_CLICK)
	    

        // Release plane on mouse up
	    _self.handler.setInputAction(function () {
            if (leftDownFlag === true && pointDraged != null && (
            		(pointDraged.id && (pointDraged.id.point ||pointDraged.id.billboard || pointDraged.id.label ||pointDraged.id.model )) ||
            	    (pointDraged.primitive && pointDraged.primitive.gltf)
            )) {
            	if(_self.option.LEFT_UP){
            		_self.option.LEFT_UP(pointDraged);
            	}
            }
            leftDownFlag = false;
            pointDraged = null;
            _self.viewer.scene.screenSpaceCameraController.enableInputs = true;
            _self.viewer.scene.screenSpaceCameraController.enableRotate = true;//锁定相机
            
        }, Cesium.ScreenSpaceEventType.LEFT_UP);
	    
	    
        // Update plane on mouse move
	    _self.handler.setInputAction(function (movement) {
            if (leftDownFlag === true && pointDraged != null && (
            		(pointDraged.id && (pointDraged.id.point ||pointDraged.id.billboard || pointDraged.id.label ||pointDraged.id.model )) ||
            	    (pointDraged.primitive && pointDraged.primitive.gltf)
            )) {
    	    	_self.cesiumTips.showAt(movement.endPosition, `<div class="con" style="color: white;">拖拽中！</div>`);
    	    	var cartesian3 =VFG.Util.getScreenToC3(_self.viewer,movement.endPosition,_self.noPickEntity);
                if(_self.option.mouseMove && cartesian3){
                	if(pointDraged.id.id){
                		_self.option.mouseMove(pointDraged.id.id,cartesian3);
                	}
                	else if(pointDraged.primitive.gltf){
                		_self.option.mouseMove(pointDraged.id,cartesian3);
                	}
                }
                
            }else{
    	    	_self.cesiumTips.showAt(movement.endPosition, `<div class="con" style="color: white;">按下鼠标左键拖拽，右键退出！</div>`);
            }
        }, Cesium.ScreenSpaceEventType.MOUSE_MOVE);
	    
	    //右键点击操作
	    _self.handler.setInputAction(function (click) {
	    	_self.destroy();
	    }, Cesium.ScreenSpaceEventType.RIGHT_CLICK);
	};
	_.prototype.destroy = function() {
        if( this.option.end){
        	this.option.end();
        };
        if( this.handler){
        	this.handler.destroy();
        	this.handler = null;
        };
        if( this.cesiumTips){
        	this.cesiumTips.destroy();
        	this.cesiumTips=null;
        };
		delete this.ops,
		delete this.cesiumTips,
		delete this.handler;
		return Cesium.destroyObject(this);
	};
	cesium.Drag = _;
})

;
///<jscompress sourcefile="CesiumDraw.js" />
/*  *  *  *  *  *  *  *  *  *  *
 *     绘制点
 *  *  *  *  *  *  *  *  *  *  */
!function(e, t) {
	"object" == typeof exports && "object" == typeof module ? module.exports = t(require("Cesium"))
			: "function" == typeof define && define.amd ? define([ "Cesium" ],
					t)
					: "object" == typeof exports ? exports.CesiumDrawPoint = t(require("Cesium"))
							: e.CesiumDrawPoint = t(e.Cesium)
}("undefined" != typeof self ? self : this, function(cesium) {
	function _(viewer, option) {
		this.viewer = viewer;
		this.option = option;
		if(!this.viewer){
			console.log('参数必填！！！');
			return;
		}
		this.cesiumTips=new Cesium.Tip(this.viewer);
		this.init();
	}
	_.prototype.init = function() {
		var _self = this;
		_self.handler = new Cesium.ScreenSpaceEventHandler(this.viewer.scene.canvas);
	    //左键点击操作
	    _self.handler.setInputAction(function (click) {
	        var cartesian3 =VFG.Util.getScreenToC3(_self.viewer,click.position,_self.primitive);
	        if (Cesium.defined(cartesian3)){
		        if( _self.option.pick){
		        	 _self.option.pick(cartesian3);
		        }
	        }
	    }, Cesium.ScreenSpaceEventType.LEFT_CLICK);
	    
	    //鼠标移动事件
	    _self.handler.setInputAction(function (movement) {
	    	_self.cesiumTips.showAt(movement.endPosition, `<div class="con" style="color: white;">点击添加点，右键退出！</div>`);
	    }, Cesium.ScreenSpaceEventType.MOUSE_MOVE);

	    //右键点击操作
	    _self.handler.setInputAction(function (click) {
	    	_self.destroy();

	    }, Cesium.ScreenSpaceEventType.RIGHT_CLICK);
	};
	_.prototype.destroy = function() {
        if( this.option.end){
        	this.option.end();
        };
        if( this.handler){
        	this.handler.destroy();
        	this.handler = null;
        };
        if( this.cesiumTips){
        	this.cesiumTips.destroy();
        	this.cesiumTips=null;
        };
		delete this.ops,
		delete this.cesiumTips,
		delete this.handler;
		return Cesium.destroyObject(this);
	};
	cesium.DrawPoint = _;
})

/*  *  *  *  *  *  *  *  *  *  *
 *     绘制线 
 *  *  *  *  *  *  *  *  *  *  */
!function(e, t) {
	"object" == typeof exports && "object" == typeof module ? module.exports = t(require("Cesium"))
			: "function" == typeof define && define.amd ? define([ "Cesium" ],
					t)
					: "object" == typeof exports ? exports.CesiumDrawLine = t(require("Cesium"))
							: e.CesiumDrawLine = t(e.Cesium)
}("undefined" != typeof self ? self : this, function(cesium) {
	function _(viewer, option) {
		this.viewer = viewer;
		this.option = option;
		if(!this.viewer){
			console.log('参数必填！！！');
			return;
		}
		//坐标存储
		this.cesiumTips=new Cesium.Tip(this.viewer);
		this.positions= [];
		this.primitive=undefined;
		this.init();
	}
	_.prototype.init = function() {
		var _self = this;
		_self.handler = new Cesium.ScreenSpaceEventHandler(this.viewer.scene.canvas);
		//左键点击操作
	    _self.handler.setInputAction(function (movement) {
	        var cartesian3 =VFG.Util.getScreenToC3(_self.viewer,movement.position,_self.primitive);
	        if (Cesium.defined(cartesian3)){
	            if (_self.positions.length == 0) {
	            	_self.positions.push(cartesian3.clone());
	            }
                if(_self.option.leftClick){
                	_self.option.leftClick(cartesian3);
                }
                _self.positions.push(cartesian3);
	        }
	    }, Cesium.ScreenSpaceEventType.LEFT_CLICK);
	    
	    //鼠标移动事件
	    _self.handler.setInputAction(function (movement) {
	    	_self.cesiumTips.showAt(movement.endPosition, `<div class="con" style="color: white;">单击开始绘制，右键退出！</div>`);
	    	var cartesian3 =VFG.Util.getScreenToC3(_self.viewer,movement.endPosition,_self.primitive);
            if (_self.positions.length >= 2) {
            	if(Cesium.defined(cartesian3)){
                    _self.positions.pop();
                //    cartesian3.y += (1 + Math.random());
                    _self.positions.push(cartesian3);
                    if(_self.option.mouseMove){
                    	_self.option.mouseMove(_self.positions);
                    }
            	}

            }
	    }, Cesium.ScreenSpaceEventType.MOUSE_MOVE);

	    //右键点击操作
	    _self.handler.setInputAction(function (click) {
	    	if( _self.positions){
    		  _self.positions.pop();
              if(_self.option.mouseMove){
              	_self.option.mouseMove(_self.positions);
              }
	    	}
	    	_self.destroy();
	    }, Cesium.ScreenSpaceEventType.RIGHT_CLICK);
	};
	_.prototype.destroy = function() {
        if( this.option.end){
        	this.option.end();
        };
        if( this.handler){
        	this.handler.destroy();
        	this.handler = null;
        };
        if( this.cesiumTips){
        	this.cesiumTips.destroy();
        	this.cesiumTips=null;
        };
		delete this.ops,
		delete this.cesiumTips,
		delete this.handler;
		return Cesium.destroyObject(this);
	};
	cesium.DrawLine = _;
})

/**
 * 绘制多边形
 */
!function(e, t) {
	"object" == typeof exports && "object" == typeof module ? module.exports = t(require("Cesium"))
			: "function" == typeof define && define.amd ? define([ "Cesium" ],
					t)
					: "object" == typeof exports ? exports.CesiumDrawPolygon = t(require("Cesium"))
							: e.CesiumDrawPolygon = t(e.Cesium)
}("undefined" != typeof self ? self : this, function(cesium) {
	function _(viewer, option) {
		this.viewer = viewer;
		this.option = option;
		if(!this.viewer){
			console.log('参数必填！！！');
			return;
		}
		//坐标存储
		this.cesiumTips=new Cesium.Tip(this.viewer);
		this.positions= [];
		this.primitive=undefined;
		this.init();
	}
	_.prototype.init = function() {
		var _self = this;
		_self.handler = new Cesium.ScreenSpaceEventHandler(this.viewer.scene.canvas);
		//左键点击操作
	    _self.handler.setInputAction(function (movement) {
	        var cartesian3 =VFG.Util.getScreenToC3(_self.viewer,movement.position,_self.primitive);
	        if (Cesium.defined(cartesian3)){
	            if (_self.positions.length == 0) {
	            	_self.positions.push(cartesian3.clone());
	            }
                if(_self.option.leftClick){
                	_self.option.leftClick(cartesian3);
                }
                _self.positions.push(cartesian3);
	        }
	        
	    }, Cesium.ScreenSpaceEventType.LEFT_CLICK);
	    
	    //鼠标移动事件
	    _self.handler.setInputAction(function (movement) {
	    	_self.cesiumTips.showAt(movement.endPosition, `<div class="con" style="color: white;">单击开始绘制，右键退出！</div>`);
	    	var cartesian3 =VFG.Util.getScreenToC3(_self.viewer,movement.endPosition,_self.primitive);
            if (_self.positions.length >= 2) {
            	if(Cesium.defined(cartesian3)){
                    _self.positions.pop();
                    _self.positions.push(cartesian3);
                    if(_self.option.mouseMove){
                    	_self.option.mouseMove(_self.positions);
                    }
            	}

            }
	    }, Cesium.ScreenSpaceEventType.MOUSE_MOVE);

	    //右键点击操作
	    _self.handler.setInputAction(function (click) {
	    	if( _self.positions){
	    		  _self.positions.pop();
	              if(_self.option.mouseMove){
	              	_self.option.mouseMove(_self.positions);
	              }
		    	}
	    	_self.destroy();
	    }, Cesium.ScreenSpaceEventType.RIGHT_CLICK);
	};
	_.prototype.destroy = function() {
        if( this.option.end){
        	this.option.end();
        };
        if( this.handler){
        	this.handler.destroy();
        	this.handler = null;
        };
        if( this.cesiumTips){
        	this.cesiumTips.destroy();
        	this.cesiumTips=null;
        };
		delete this.ops,
		delete this.cesiumTips,
		delete this.handler;
		return Cesium.destroyObject(this);
	};
	cesium.DrawPolygon = _;
})

/**
 * 绘制模型
 */
!function(e, t) {
	"object" == typeof exports && "object" == typeof module ? module.exports = t(require("Cesium"))
			: "function" == typeof define && define.amd ? define([ "Cesium" ],
					t)
					: "object" == typeof exports ? exports.CesiumDrawModel = t(require("Cesium"))
							: e.CesiumDrawModel = t(e.Cesium)
}("undefined" != typeof self ? self : this, function(cesium) {
	function _(viewer, option) {
		this.viewer = viewer;
		this.option = option;
		if(!this.viewer){
			console.log('参数必填！！！');
			return;
		}
		//坐标存储
		this.cesiumTips=new Cesium.Tip(this.viewer);
		this.primitive=undefined;
		this.init();
	}
	_.prototype.init = function() {
		var _self = this;
		_self.handler = new Cesium.ScreenSpaceEventHandler(this.viewer.scene.canvas);
		//左键点击操作
	    _self.handler.setInputAction(function (movement) {
	        var cartesian3 =VFG.Util.getScreenToC3(_self.viewer,movement.position);
	        if (Cesium.defined(cartesian3)){
                if(_self.option.leftClick){
                	_self.option.leftClick(cartesian3);
                	_self.destroy();
                }
	        }
	    }, Cesium.ScreenSpaceEventType.LEFT_CLICK);
	    
	    //鼠标移动事件
	    _self.handler.setInputAction(function (movement) {
	    	_self.cesiumTips.showAt(movement.endPosition, `<div class="con" style="color: white;">单击确定模型位置，右键退出！</div>`);
	    }, Cesium.ScreenSpaceEventType.MOUSE_MOVE);

	    //右键点击操作
	    _self.handler.setInputAction(function (click) {
	    	_self.destroy();
	    }, Cesium.ScreenSpaceEventType.RIGHT_CLICK);
	};
	_.prototype.destroy = function() {
        if( this.option.end){
        	this.option.end();
        };
        if( this.handler){
        	this.handler.destroy();
        	this.handler = null;
        };
        if( this.cesiumTips){
        	this.cesiumTips.destroy();
        	this.cesiumTips=null;
        };
		delete this.ops,
		delete this.cesiumTips,
		delete this.handler;
		return Cesium.destroyObject(this);
	};
	cesium.DrawModel = _;
});
///<jscompress sourcefile="CesiumTip.js" />
/*  *  *  *  *  *  *  *  *  *  *
 *     Tip      *
 *  *  *  *  *  *  *  *  *  *  */
!function(e, t) {
	"object" == typeof exports && "object" == typeof module ? module.exports = t(require("Cesium"))
			: "function" == typeof define && define.amd ? define([ "Cesium" ],
					t)
					: "object" == typeof exports ? exports.CesiumMQTT = t(require("Cesium"))
							: e.CesiumMQTT = t(e.Cesium)
}("undefined" != typeof self ? self : this, function(cesium) {
	function _(viewer, options) {
		this.viewer = viewer;
		this.options = options;
		this.frameDiv=this.viewer.cesiumWidget.container;
		this.isInit=false;
		this.init();
	}
	_.prototype.init = function() {
		var _self = this;
	    if (_self.isInit) { return; }
	    var div = document.createElement('DIV');
	    div.className = "toolTip-left";
	    var title = document.createElement('DIV');
	    title.className = "tooltipdiv-inner";
	    div.appendChild(title);
	    _self._div = div;
	    _self._title = title;
	    _self.frameDiv.appendChild(div);
	    _self.isInit = true;
	};
	_.prototype.setVisible = function(visible) {
		var _self = this;
	    if (!_self.isInit) { return; }
	    _self._div.style.display = visible ? 'block' : 'none';
	};
	_.prototype.showAt = function (position, message) {
		var _self = this;
	    if (!_self.isInit) { return; }
	    if (position && message) {
	    	_self.setVisible(true);
	    	_self._title.innerHTML = message;
	    	_self._div.style.position = "absolute"
	    	_self._div.style.left = position.x + 20 + "px";
	    	_self._div.style.top = (position.y - this._div.clientHeight/2) + "px";
	    }
    };
	_.prototype.destroy = function() {
		var _self = this;
		if( _self._div){
			$( _self._div).remove();
		}
		if( _self._title){
			$( _self._title).remove();
		}
		return Cesium.destroyObject(this);
	};
	cesium.Tip = _;
});
///<jscompress sourcefile="VFGUtil.js" />
VFG.Util=function(){
}
//存放容器
VFG.Util.primitiveMap = new Map();

VFG.Util.getUuid = function() {
	var s = [];
	var hexDigits = "0123456789abcdef";
	for (var i = 0; i < 36; i++) {
		s[i] = hexDigits.substr(Math.floor(Math.random() * 0x10), 1);
	}
	s[14] = "4"; 
	s[19] = hexDigits.substr((s[19] & 0x3) | 0x8, 1); 
	s[8] = s[13] = s[18] = s[23] = "-";
	var uuid = s.join("");
	return uuid;
};



/**
 * 删除数组
 * index：数组中需要删除数据的起始位置；n：需要删除的元素，数据的个数。
 */
VFG.Util.splice = function(arr,index, n) {
	if(arr){
		arr.splice(index, n);
	}
	return arr;
};
/**
 * 插入
 */
VFG.Util.inset = function(arr,index,data) {
	if(arr){
		arr.splice(index,0,data);
	}
	return arr;
};

/**
 * 替换
 */
VFG.Util.replace = function(arr,n,data) {
	if(arr){
		arr.splice(index,n,data);
	}
	return arr;
};

/**
 * 场景截图
 */
VFG.Util.getSceneImg = function (viewer,width,height) {
	var canvas = viewer.scene.canvas;
    var imageWidth = width?width:800;
    var img = Canvas2Image.convertToImage(canvas, imageWidth, height?height:imageWidth * canvas.height / canvas.width,'png');
    return img.src
}

/**
 * 获取视角
 */
VFG.Util.getVisualAngle=function(viewer) {
	return {
		heading:viewer.camera.heading,
		pitch:viewer.camera.pitch,
		roll:viewer.camera.roll,
		position:viewer.camera.position
	}
};

VFG.Util.removeEntityById=function(viewer,uniqueId) {
	viewer.entities.removeById(uniqueId);
};

VFG.Util.getEntityById=function(viewer,uniqueId) {
	return viewer.entities.getById(uniqueId);
};

VFG.Util.getEntityById=function(viewer,uniqueId) {
	return viewer.entities.getById(uniqueId);
};

VFG.Util.getCenterPoint= function(cartesianA,cartesianB) {
	var _self = this;
	let AtoB = Cesium.Cartesian3.subtract(cartesianA, cartesianB, new Cesium.Cartesian3());
	let cartesian4_1 = Cesium.Cartesian3.divideByScalar(AtoB, 2, new Cesium.Cartesian3())
	let cartesianC= Cesium.Cartesian3.add(cartesian4_1, cartesianB, new Cesium.Cartesian3());
    return cartesianC;
}

/**
 * 经纬度获取屏幕坐标
 */
VFG.Util.getC2FormLnLa = function(viewer,position) {
	return Cesium.SceneTransforms.wgs84ToWindowCoordinates(viewer.scene,this.getC3FormLnLa(position))
}


/**
 * 经纬度转笛卡尔坐标
 * position:{
 * 	x:经度
 *  y:维度
 *  z:高度
 * }
 */
VFG.Util.getC3FormLnLa = function(position) {
	return Cesium.Cartesian3.fromDegrees(position.x*1,position.y*1,position.z*1);
}

/**
 * 笛卡尔坐标转经纬度
 */
VFG.Util.getLnLaFormC3 = function(viewer,cartesian3) {
	var ellipsoid=viewer.scene.globe.ellipsoid;
	var cartographic=ellipsoid.cartesianToCartographic(cartesian3);
	var lat=Cesium.Math.toDegrees(cartographic.latitude);
	var lng=Cesium.Math.toDegrees(cartographic.longitude);
	var alt=cartographic.height;
	return {
		x:lng,
		y:lat,
		z:alt
	};
}


/**
 * 获取鼠标当前的屏幕坐标位置的三维Cesium坐标
 * @param {Cesium.Scene} scene 
 * @param {Cesium.Cartesian2} position 二维屏幕坐标位置
 * @param {Cesium.Entity} noPickEntity 排除的对象（主要用于绘制中，排除对自己本身的拾取）
 */
VFG.Util.getScreenToC3=function(viewer, position, noPickEntity) {
	var scene = viewer.scene;
	var cartesian3;
	
	if (scene.mode !== Cesium.SceneMode.MORPHING) {
		var pickedObject = scene.pick(position);
		if (scene.pickPositionSupported && Cesium.defined(pickedObject)) {
			if(!this.hasPickedModel(pickedObject,noPickEntity)){
				//viewer.scene.globe.depthTestAgainstTerrain = true;
				cartesian3 = viewer.scene.pickPosition(position);
				//viewer.scene.globe.depthTestAgainstTerrain = false;
				if (Cesium.defined(cartesian3)) {
/*	                var cartographic = Cesium.Cartographic.fromCartesian(cartesian3);
	                var lng = Cesium.Math.toDegrees(cartographic.longitude);
	                var lat = Cesium.Math.toDegrees(cartographic.latitude);
	                var height = cartographic.height;//模型高度
					var sampleHeight = viewer.scene.sampleHeight(cartographic);*/
	                return cartesian3;
	            }
/*				if(Cesium.defined(cartesian3)){
					var LnLa=VFG.Util.getC3ToLnLa(viewer, cartesian3);
					var sampleHeight = viewer.scene.sampleHeight(Cesium.Cartographic.fromCartesian(cartesian3));
					return Cesium.Cartesian3.fromDegrees(LnLa.x, LnLa.y,sampleHeight);
				}*/
			}
		}
	}
	
	//获取地形表面的经纬度高程坐标：
	if (!Cesium.defined(cartesian3) &&  (viewer.scene)) {
		var ray = viewer.camera.getPickRay(position);
		if (Cesium.defined(ray)) {
			cartesian3 = viewer.scene.globe.pick(ray, viewer.scene);
			return cartesian3;
		}

	}
	
	//二维坐标，获取椭球体表面的经纬度坐标：
	if (!Cesium.defined(cartesian3)) {
		cartesian3 = viewer.scene.camera.pickEllipsoid(position,viewer.scene.globe.ellipsoid);
		return cartesian3;
	}
	return cartesian3;
}



/**
 * 模型矩阵转笛卡尔坐标
 */
VFG.Util.modelMatrixToC3=function (modelMatrix){
	var cartesian3=new Cesium.Cartesian3();
	Cesium.Matrix4.getTranslation(modelMatrix,cartesian3);//根据最终变换矩阵m得到p2
	return cartesian3
}

VFG.Util.modelMatrixToRotate=function (modelMatrix){
    var m1 = Cesium.Transforms.eastNorthUpToFixedFrame(Cesium.Matrix4.getTranslation(modelMatrix, new Cesium.Cartesian3()), Cesium.Ellipsoid.WGS84, new Cesium.Matrix4());
    // 矩阵相除
    var m3 = Cesium.Matrix4.multiply(Cesium.Matrix4.inverse(m1, new Cesium.Matrix4()), modelMatrix, new Cesium.Matrix4());
    // 得到旋转矩阵
    var mat3 = Cesium.Matrix4.getMatrix3(m3, new Cesium.Matrix3());
    // 计算四元数
    var q = Cesium.Quaternion.fromRotationMatrix(mat3);
    // 计算旋转角(弧度)
    var hpr = Cesium.HeadingPitchRoll.fromQuaternion(q);
    // 得到角度
    var heading = Cesium.Math.toDegrees(hpr.heading).toFixed(2)*1;;
    var pitch = Cesium.Math.toDegrees(hpr.pitch).toFixed(2)*1;;
    var roll = Cesium.Math.toDegrees(hpr.roll).toFixed(2)*1;;
    if(heading<0){
    	heading+=360;
    }
    if(pitch<0){
    	pitch+=360;
    }
    if(roll<0){
    	roll+=360;
    }
	return {x:pitch,y:heading,z:roll}
}


VFG.Util.modelMatrixToHeadingPitchRoll=function (modelMatrix){
    var m1 = Cesium.Transforms.eastNorthUpToFixedFrame(Cesium.Matrix4.getTranslation(modelMatrix, new Cesium.Cartesian3()), Cesium.Ellipsoid.WGS84, new Cesium.Matrix4());
    // 矩阵相除
    var m3 = Cesium.Matrix4.multiply(Cesium.Matrix4.inverse(m1, new Cesium.Matrix4()), modelMatrix, new Cesium.Matrix4());
    // 得到旋转矩阵
    var mat3 = Cesium.Matrix4.getMatrix3(m3, new Cesium.Matrix3());
    // 计算四元数
    var q = Cesium.Quaternion.fromRotationMatrix(mat3);
    // 计算旋转角(弧度)
    var headingPitchRoll = Cesium.HeadingPitchRoll.fromQuaternion(q);
	return headingPitchRoll;
}

/**
 * 判断是否包含本身
 */
VFG.Util.hasPickedModel=function(pickedObject, noPickEntity) {
    if (Cesium.defined(pickedObject.id)) {
        //entity 
        var entity = pickedObject.id;
        if (entity._noMousePosition) return entity; //排除标识不拾取的对象
        if (noPickEntity && entity == noPickEntity) return entity;
    }

    if (Cesium.defined(pickedObject.primitive)) {
        var primitive = pickedObject.primitive;
        if (primitive._noMousePosition) return primitive; //排除标识不拾取的对象
        if (noPickEntity && primitive == noPickEntity) return primitive;
    }

    return null;
}


VFG.Util.getScreenToLnLa  = function(viewer, position) {
	var scene = viewer.scene;
	var cartesian3;
	if (scene.mode !== Cesium.SceneMode.MORPHING) {
		var pickedObject = scene.pick(position);
		if (scene.pickPositionSupported && Cesium.defined(pickedObject)) {
			cartesian3 = viewer.scene.pickPosition(position);
		}
	}

	if (!Cesium.defined(cartesian3)
			&& Cesium.Entity.supportsPolylinesOnTerrain(viewer.scene)) {
		var ray = viewer.camera.getPickRay(position);
		if (Cesium.defined(ray)) {
			cartesian3 = viewer.scene.globe.pick(ray, viewer.scene);
		}

	}
	if (!Cesium.defined(cartesian3)) {
		cartesian3 = viewer.scene.camera.pickEllipsoid(position,
				viewer.scene.globe.ellipsoid);
	}
	return cartesian3;
}

/**
 * 经纬度转笛卡尔坐标
 */
VFG.Util.getC3ToLnLa  = function(viewer, cartesian3) {
	var ellipsoid=viewer.scene.globe.ellipsoid;
	var cartographic=ellipsoid.cartesianToCartographic(cartesian3);
	var lat=Cesium.Math.toDegrees(cartographic.latitude);
	var lng=Cesium.Math.toDegrees(cartographic.longitude);
	var alt=cartographic.height;
	return {x:lng,y:lat,z:alt};
}

/**
 * 屏幕坐标
 */
VFG.Util.getCartesian2 = function(x,y) {
	var _this=this;
	if(Cesium.defined(x) && Cesium.defined(y) ){
		return new Cesium.Cartesian2(x*1,y*1)
	}
	return null;
};

/**
 * 笛卡尔坐标
 */
VFG.Util.getCartesian3 = function(x,y,z) {
	var _this=this;
	if(Cesium.defined(x) && Cesium.defined(y) && Cesium.defined(z)){
		return new Cesium.Cartesian3(x*1,y*1,z*1)
	}
	return null;
};

VFG.Util.getDistanceDisplayCondition = function(x,y) {
	var _this=this;
	if(Cesium.defined(x) && Cesium.defined(y) ){
		return new Cesium.DistanceDisplayCondition(x*1,y*1)
	}
	return null;
};
VFG.Util.getNearFarScalar = function(near, nearValue, far, farValue) {
	var _this=this;
	if(Cesium.defined(near) && Cesium.defined(nearValue) && Cesium.defined(far) && Cesium.defined(farValue)){
		return new Cesium.NearFarScalar(near*1, nearValue*1, far*1, farValue*1);
	}
	return null;
};

VFG.Util.getHorizontalOrigin = function(value){
	if("0"===value){
		return  Cesium.HorizontalOrigin.CENTER ;
	}
	else if("1"===value){
		return  Cesium.HorizontalOrigin.LEFT  ;
	}
	else if("2"===value){
		return  Cesium.HorizontalOrigin.RIGHT  ;
	}
	else{
		return  Cesium.HorizontalOrigin.CENTER;
	}
} 
VFG.Util.getHeightReference = function(value){
	if("0"===value){
		return  Cesium.HeightReference.NONE ;
	}
	else if("1"===value){
		return  Cesium.HeightReference.CLAMP_TO_GROUND  ;
	}
	else if("2"===value){
		return  Cesium.HeightReference.RELATIVE_TO_GROUND  ;
	}
	else{
		return  Cesium.HorizontalOrigin.NONE;
	}
}	
VFG.Util.getVerticalOrigin = function(value){
	if("0"===value){
		return  Cesium.VerticalOrigin.BASELINE;
	}
	else if("1"===value){
		return  Cesium.VerticalOrigin.BOTTOM ;
	}
	else if("2"===value){
		return  Cesium.VerticalOrigin.CENTER ;
	}
	else if("3"===value){
		return  Cesium.VerticalOrigin.VerticalOrigin;
	}else{
		return  Cesium.VerticalOrigin.BASELINE;
	}
}

VFG.Util.getEntityForLine = function(data) {
	if(!data){
		return null;
	}
    var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(data.distanceDisplayConditionX,data.distanceDisplayConditionY);
    var material=VFG.Util.getMaterialForLine(data);
    if(!material){
		return null;
	}
    
    return{
        show: true,
        positions: data.positions?data.positions:[],
		width : data.width*1,
		loop:data.loop&&data.loop=='1'?true:false,
		clampToGround:data.clampToGround&&data.clampToGround=='1'?true:false,
		material:material?material:Cesium.Color.RED,
		distanceDisplayCondition : distanceDisplayCondition?distanceDisplayCondition:undefined,
		zIndex: data.sort*1,		
	}
};


VFG.Util.getMaterialForLine = function(style){
	var _this=this;
	if(Cesium.defined(style)){
		if(style.materialType=="solid"){
			return (style.color)?Cesium.Color.fromCssColorString(style.color):Cesium.Color.RED;//线条颜色;
		}
		else if(style.materialType=="dash"){
			return new Cesium.PolylineDashMaterialProperty({
				color:(style.color)?Cesium.Color.fromCssColorString(style.color):Cesium.Color.RED,//线条颜色
				gapColor:(style.gapColor)?Cesium.Color.fromCssColorString(style.gapColor):Cesium.Color.WHITE,//间隔颜色
				dashLength:(style.dashLength)?style.dashLength*1:5,//间隔距离
				dashPattern:(style.dashPattern)?style.dashPattern*1:255
			})
		}
		else if(style.materialType=="outline"){
			return new Cesium.PolylineOutlineMaterialProperty({
				color:(style.color)?Cesium.Color.fromCssColorString(style.color):Cesium.Color.RED,//线条颜色
				outlineWidth: (style.outlineWidth)?style.outlineWidth*1:5,
				outlineColor:(style.outlineColor)?Cesium.Color.fromCssColorString(style.outlineColor):Cesium.Color.WHITE,//线条颜色
			});
		}
		else if(style.materialType=="glow"){
			return new Cesium.PolylineGlowMaterialProperty({
					color:(style.color)?Cesium.Color.fromCssColorString(style.color):Cesium.Color.RED,//线条颜色
					glowPower: (style.glowPower)?style.glowPower*1:0.5,//发光强度
				});
		}
		else if(style.materialType=="arrow"){
			return new Cesium.PolylineArrowMaterialProperty(
					(style.color)?Cesium.Color.fromCssColorString(style.color):Cesium.Color.RED
			);
		}
		else if(style.materialType=="od"){
			initPolylineTrailLinkMaterialProperty({type:style.odType});
			return new Cesium.PolylineTrailLinkMaterialProperty(
					(style.color)?Cesium.Color.fromCssColorString(style.color):Cesium.Color.RED,style.interval?style.interval*1000:20000)
		}
		else{
			return Cesium.Color.BLUE;
		}
	}
}

VFG.Util.getEntityForPolygon = function(data) {
	var _this=this;
	var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(data.distanceDisplayConditionX*1,data.distanceDisplayConditionY*1);
	
	var options={
		stRotation:data.stRotation?data.stRotation:0.0,
		fill:data.fill?data.fill:false,
		material:data.color? Cesium.Color.fromCssColorString(data.color):Cesium.Color.BLACK,
		outline:data.outline && data.outline=='1'  ?true:false,
		outlineColor:data.outlineColor? Cesium.Color.fromCssColorString(data.outlineColor):Cesium.Color.BLACK,
		outlineWidth:data.outlineWidth?data.outlineWidth*1:0.0,
		closeTop:data.closeTop?data.closeTop:false,
		closeBottom:data.closeBottom?data.closeBottom:false,
		arcType:Cesium.ArcType.GEODESIC,
		shadows:data.shadows?data.shadows:false,
		distanceDisplayCondition:distanceDisplayCondition||null,
		classificationType:_this.getClassificationType(data.classificationType)
	}
	
	var perPositionHeight=data.perPositionHeight && data.perPositionHeight=='1'  ?true:false;
	if(perPositionHeight){
		 options.height=data.height?data.height:0.0;
		 options.perPositionHeight=perPositionHeight;
		 options.heightReference=_this.getHeightReference(data.heightReference);
		 options.extrudedHeight=data.extrudedHeight?data.extrudedHeight:0.0;
		 options.extrudedHeightReference=_this.getHeightReference(data.extrudedHeightReference);
	}
	return options;
};

VFG.Util.getClassificationType = function(value) {
	if('1'==value){
		return Cesium.ClassificationType.TERRAIN;
	}
	else if('2'==value){
		return Cesium.ClassificationType.CESIUM_3D_TILE;
	}else{
		return Cesium.ClassificationType.BOTH;
	}
};

/**
 * 创建线段
 */
VFG.Util.createLinePrimitive=function(viewer,ops,polyline){
	if(polyline){
		return primitive =viewer.entities.add({
        	id:ops.id,
        	name:ops.name||'线',
        	show: true,
        	bizType:ops.code||'',
            polyline: polyline
        });
	}else{
		return primitive =viewer.entities.add({
        	id:ops.id,
        	name:ops.name||'线',
        	bizType:ops.code||'',
            polyline: {
                show: true,
                positions:ops.positions||[],
                material:Cesium.Color.RED,
                width:2
            }
        });
	}
}

/***
 * 创建多边形
 */
VFG.Util.createPolygonPrimitive=function(viewer,ops,polygon){
	viewer.entities.removeById(ops.id);
	if(polygon){
		return viewer.entities.add({
        	id:ops.id,
        	name:ops.name||'多边形',
        	show: true,
        	polygon: polygon
        });
	}else{
		return viewer.entities.add({
        	id:ops.id,
        	name:ops.name||'多边形',
        	show: true,
            polygon:{
                hierarchy : ops.hierarchy||[],
                perPositionHeight: true,
                material: Cesium.Color.RED.withAlpha(0.7),
                outline: true,
                outlineColor: Cesium.Color.YELLOW.withAlpha(1)
            }
        });
	}
}

VFG.Util.getHeightReference=function(value){
	if('RELATIVE_TO_GROUND'==value){
		return Cesium.HeightReference.RELATIVE_TO_GROUND;
	}
	else if('CLAMP_TO_GROUND'==value){
		return Cesium.HeightReference.CLAMP_TO_GROUND;
	}else{
		return Cesium.HeightReference.NONE;
	}
}

/**
 * 创建模型ForGLTF
 */
VFG.Util.createGltfPrimitive=function(viewer,ops){
	if(!ops){
		console.log('参数必填!!!');
		return;
	}
	
	if(!ops.uri){
		console.log('模型地址必填!!!');
		return;
	}
	
	if('GLTF'!=ops.type){
		console.log('模型格式必需是GLTF!!!');
		return;
	}
	if(!(ops.posX && ops.posY && ops.posZ)){
		console.log('坐标必填!!!');
		return;
	}
	if(!this.primitiveMap.has(ops.id)){
		var heading = Cesium.defaultValue(ops.heading, 0.0);
	    var pitch = Cesium.defaultValue(ops.pitch, 0.0);
	    var roll = Cesium.defaultValue(ops.roll, 0.0);
	    var headingPitchRoll = new Cesium.HeadingPitchRoll(Cesium.Math.toRadians(heading), Cesium.Math.toRadians(pitch), Cesium.Math.toRadians(roll));
		var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(ops.displayNear,ops.displayFar);
		var origin = Cesium.Cartesian3.fromDegrees(ops.posX*1, ops.posY*1,ops.posZ*1);
		var modelMatrix =Cesium.Transforms.headingPitchRollToFixedFrame(origin, headingPitchRoll, Cesium.Ellipsoid.WGS84, Cesium.Transforms.eastNorthUpToFixedFrame, new Cesium.Matrix4());
		var model = viewer.scene.primitives.add(Cesium.Model.fromGltf({
			id:ops.id,
			name:ops.name||'未命名',
			url: ops.uri,
			type:ops.type,
			bizType:ops.code||'',
			show : ( ops.show &&  ops.show!='1')?false : true,                     
			modelMatrix : modelMatrix,
			scale: ops.scale*1||1,
			minimumPixelSize:(ops.minimumPixelSize)?ops.minimumPixelSize*1:0,
			maximumScale:(ops.minimumPixelSize)?ops.minimumPixelSize*1:undefined,
			allowPicking : true,        
			debugShowBoundingVolume : false, 
			debugWireframe : false,
			distanceDisplayCondition:distanceDisplayCondition?distanceDisplayCondition:undefined,
		}));
		model.readyPromise.then(function(model) {
		  model.activeAnimations.addAll();
		}).otherwise(function(error){
	    });
		this.primitiveMap.set(ops.id,model);
		return model;
	}else{
		return this.primitiveMap.get(ops.id);
	}
	
/*    var distanceDisplayCondition =VFG.Util.getDistanceDisplayCondition(ops.displayNear,ops.displayFar);
	var position = Cesium.Cartesian3.fromDegrees(ops.posX*1, ops.posY*1,ops.posZ*1)
	var entity=new Cesium.Entity({
		id:ops.id,
    	name:ops.name||'未命名',
	    show: true,
	    position: position,
	    orientation:Cesium.Transforms.headingPitchRollQuaternion(
    		 position,
	         new Cesium.HeadingPitchRoll(
	            Cesium.Math.toRadians(ops.heading*1||0), 
	            Cesium.Math.toRadians(ops.pitch*1||0),
	            Cesium.Math.toRadians(ops.roll*1||0)
			 )
	    ),
	    model:{
	    	uri: ops.uri,
	    	basePath: ops.basePath||'',
	    	scale: ops.scale*1||1,
	    	allowPicking:(ops.allowPicking && ops.allowPicking=='1')?true:false,
			minimumPixelSize:(ops.minimumPixelSize)?ops.minimumPixelSize*1:0,
			maximumScale:(ops.minimumPixelSize)?ops.minimumPixelSize*1:undefined,
		    distanceDisplayCondition:distanceDisplayCondition?distanceDisplayCondition:undefined,
		    HeightReference:this.getHeightReference(ops.heightReference)
	    }
	});*/
	//return viewer.entities.add(entity)
}

VFG.Util.getPrimitiveModelMatrix=function(ops){
	var heading = Cesium.defaultValue(ops.heading, 0.0);
	var pitch = Cesium.defaultValue(ops.pitch, 0.0);
	var roll = Cesium.defaultValue(ops.roll, 0.0);
	var headingPitchRoll = new Cesium.HeadingPitchRoll(Cesium.Math.toRadians(heading), Cesium.Math.toRadians(pitch), Cesium.Math.toRadians(roll));
	var origin = Cesium.Cartesian3.fromDegrees(ops.posX*1, ops.posY*1,ops.posZ*1);
	return Cesium.Transforms.headingPitchRollToFixedFrame(origin, headingPitchRoll, Cesium.Ellipsoid.WGS84, Cesium.Transforms.eastNorthUpToFixedFrame, new Cesium.Matrix4());
}


VFG.Util.updatePrimitiveModelMatrix=function(ops){
	var heading = Cesium.defaultValue(ops.heading, 0.0);
	var pitch = Cesium.defaultValue(ops.pitch, 0.0);
	var roll = Cesium.defaultValue(ops.roll, 0.0);
    //旋转
   var mx = Cesium.Matrix3.fromRotationX(pitch);
   var my = Cesium.Matrix3.fromRotationY(heading);
   var mz = Cesium.Matrix3.fromRotationZ(roll);
   var rotationX = Cesium.Matrix4.fromRotationTranslation(mx);
   var rotationY = Cesium.Matrix4.fromRotationTranslation(my);
   var rotationZ = Cesium.Matrix4.fromRotationTranslation(mz);
   //平移
   var origin = Cesium.Cartesian3.fromDegrees(ops.posX*1, ops.posY*1,ops.posZ*1);
   var m = Cesium.Transforms.eastNorthUpToFixedFrame(origin);
   //旋转、平移矩阵相乘
   Cesium.Matrix4.multiply(m, rotationX, m);
   Cesium.Matrix4.multiply(m, rotationY, m);
   Cesium.Matrix4.multiply(m, rotationZ, m);
   return m;
}

VFG.Util.create3DTilePrimitive=function(viewer,ops){
	if(!ops){
		console.log('参数必填!!!');
		return;
	}
	
	if(!ops.uri){
		console.log('模型地址必填!!!');
		return;
	}
	
	if('3DTILES'!=ops.type){
		console.log('模型格式必需是3DTILES!!!');
		return;
	}
	
	
	if(!this.primitiveMap.has(ops.id)){
		var primitive=viewer.scene.primitives.add(new Cesium.Cesium3DTileset({
			id : ops.id,
			url : ops.uri,
			name : ops.name ||'未命名',
			show : ( ops.show &&  ops.show!='1')?false : true,    
			bizType:ops.code||'',
			preferLeaves:(ops && ops.preferLeaves && ops.preferLeaves=='1')?true:false,
			imageBasedLightingFactor :Cesium.Cartesian2(1.0, 1.0),
			loadSiblings:true,
			skipLevels:ops.skipLevels ? ops.skipLevels*1: 1,
			baseScreenSpaceError:ops.baseScreenSpaceError ? ops.baseScreenSpaceError*1: 1024,
			skipScreenSpaceErrorFactor:ops.skipScreenSpaceErrorFactor ? ops.skipScreenSpaceErrorFactor*1: 16,
			maximumMemoryUsage:ops.maximumMemoryUsage ? ops.maximumMemoryUsage*1: 512,
			maximumScreenSpaceError : ops.maximumScreenSpaceError ? ops.maximumScreenSpaceError*1: 16,
			skipLevelOfDetail : ops.skipLevelOfDetail ? (ops.skipLevelOfDetail=='on'?true:false): false,
			maximumNumberOfLoadedTiles : ops.maximumNumberOfLoadedTiles ? ops.maximumNumberOfLoadedTiles*1: 1024, //最大加载瓦片个数			
		}));
		
		primitive.readyPromise.then(function(tileset) {

			if(ops.posX && ops.posY && ops.posZ){
				  tileset._root.transform = VFG.Util.getPrimitiveModelMatrix(ops);
			}else{
	            var heightOffset =ops.z || 0;  //高度
	            var boundingSphere = tileset.boundingSphere; 
	            var cartographic = Cesium.Cartographic.fromCartesian(boundingSphere.center);
	            var surface = Cesium.Cartesian3.fromRadians(cartographic.longitude, cartographic.latitude, 0.0);
	            var offset = Cesium.Cartesian3.fromRadians(cartographic.longitude, cartographic.latitude, heightOffset);
	            var translation = Cesium.Cartesian3.subtract(offset, surface, new Cesium.Cartesian3());
	            tileset.modelMatrix = Cesium.Matrix4.fromTranslation(translation);
			}
			
			
		    if(ops.callBack){
		    	var result=VFG.Util.getCenterForModel(tileset,tileset._root.transform);
		    	ops.callBack(result);
		    }
			
		}).otherwise(function(error){
			console.log(error);
	    });
		this.primitiveMap.set(ops.id,primitive);
		return primitive;
	}else{
		return this.primitiveMap.get(ops.id);
	}
}

//获取模型的中心点信息
VFG.Util.getCenterForModel=function(tileset, transform) {
    var result = {};

    //记录模型原始的中心点
    var boundingSphere = tileset.boundingSphere;
    var position = boundingSphere.center;
    var catographic = Cesium.Cartographic.fromCartesian(position);

    var height = Number(catographic.height.toFixed(2));
    var longitude = Number(Cesium.Math.toDegrees(catographic.longitude).toFixed(6));
    var latitude = Number(Cesium.Math.toDegrees(catographic.latitude).toFixed(6));
    result = { x: longitude, y: latitude, z: height };

    //console.log("模型内部原始位置:" + JSON.stringify(result));

    //如果tileset自带世界矩阵矩阵，那么计算放置的经纬度和heading
    if (transform) {
        var matrix = Cesium.Matrix4.fromArray(tileset._root.transform);
        var pos = Cesium.Matrix4.getTranslation(matrix, new Cesium.Cartesian3());
        var wpos = Cesium.Cartographic.fromCartesian(pos);
        if (Cesium.defined(wpos)) {
            result.x = Number(Cesium.Math.toDegrees(wpos.longitude).toFixed(6));
            result.y = Number(Cesium.Math.toDegrees(wpos.latitude).toFixed(6));
            result.z = Number(wpos.height.toFixed(2));

            //取旋转矩阵
            var rotmat = Cesium.Matrix4.getMatrix3(matrix, new Cesium.Matrix3());
            //默认的旋转矩阵
            var defrotmat = Cesium.Matrix4.getMatrix3(Cesium.Transforms.eastNorthUpToFixedFrame(pos), new Cesium.Matrix3());

            //计算rotmat 的x轴，在defrotmat 上 旋转
            var xaxis = Cesium.Matrix3.getColumn(defrotmat, 0, new Cesium.Cartesian3());
            var yaxis = Cesium.Matrix3.getColumn(defrotmat, 1, new Cesium.Cartesian3());
            var zaxis = Cesium.Matrix3.getColumn(defrotmat, 2, new Cesium.Cartesian3());

            var dir = Cesium.Matrix3.getColumn(rotmat, 0, new Cesium.Cartesian3());

            dir = Cesium.Cartesian3.cross(dir, zaxis, dir);
            dir = Cesium.Cartesian3.cross(zaxis, dir, dir);
            dir = Cesium.Cartesian3.normalize(dir, dir);

            var heading = Cesium.Cartesian3.angleBetween(xaxis, dir);

            var ay = Cesium.Cartesian3.angleBetween(yaxis, dir);

            if (ay > Math.PI * 0.5) {
                heading = 2 * Math.PI - heading;
            }
            result.rotation_x = 0;
            result.rotation_y = 0;
            result.rotation_z = Number(Cesium.Math.toDegrees(heading).toFixed(1));

            result.heading = result.rotation_z; //兼容v1老版本

           // console.log("模型内部世界矩阵:" + JSON.stringify(result));
        }
    }

    return result;
}

VFG.Util.getPrimitiveById=function(viewer,id){
	if(this.primitiveMap.has(id)){
		return this.primitiveMap.get(id);
	}
	return null;
}

VFG.Util.removePrimitive=function(viewer,id){
	if(this.primitiveMap.has(id)){
		if(viewer.scene.primitives.remove(this.primitiveMap.get(id))){
			this.primitiveMap.delete(id);
			return true;
		}
		return false;
	}else{
		return false;	
	}
	return false;
}

VFG.Util.removeAllPrimitive=function(viewer){
	this.primitiveMap.clear();
	return viewer.scene.primitives.removeAll();
}

/**
 * 移除场景元素
 * viewer
 * ops:{id:图层Id,type:图层类型}
 */
VFG.Util.removeScenePrimitive=function(viewer,ops){
	if('point'==ops.type){
		VFG.Point.removePointById(ops.id) 
	}
	else if('line'==ops.type){
		VFG.Util.removeEntityById(viewer,ops.id) 
	}
	else if('polygon'==ops.type){
		VFG.Util.removeEntityById(viewer,ops.id) 
	}
	if('Feature'==ops.type){
		VFG.Model.Feature.removeFeatureById(ops.id) 
	}
	else if('map'==ops.type){
		VFG.Provider.removeById(viewer,ops.id)
	}
	else if('terrain'==ops.type){
		VFG.Provider.removeTerrainProviderById(viewer,ops.id);
	}
	else if('division'==ops.type){
		VFG.Provider.removeById(viewer,ops.id)
	}
	else if('road'==ops.type){
		VFG.Provider.removeById(viewer,ops.id)
	}
	else if('GLTF'==ops.type){
		VFG.Util.removePrimitive(viewer,ops.id);
	}
	else if('3DTILES'==ops.type){
 		VFG.Util.removePrimitive(viewer,ops.id);
	}
}

/**
 * 显示隐藏
 */
VFG.Util.showScenePrimitive=function(viewer,ops){
	if('point'==ops.type){
		var entity=VFG.Point.getPointById(ops.id);
		if(entity){
			entity.show=ops.show;
		}
	}
	else if('line'==ops.type || 'polygon'==ops.type){
		var entity=viewer.entities.getById(ops.id);
		if(entity){
			entity.show=ops.show;
		}
	}
	else if('GLTF'==ops.type || '3DTILES'==ops.type){
		if(this.primitiveMap.has(ops.id)){
			this.primitiveMap.get(ops.id).show=ops.show;
		}
	}
}


VFG.Util.c3sToLnLas=function(viewer,positions){
	var LnLas=[];
	for(var i=0;i<positions.length;i++){
		LnLas.push(this.getC3ToLnLa(viewer,positions[i]));
	}
	return LnLas;
}

VFG.Util.polygonForCreate=function(viewer,polygonRender){
	var _this=this;
	if(!polygonRender){
		return;
	}
	var polygon=polygonRender.polygon;
	var styles=polygonRender.styles;
	if(!polygon){
		return;
	}
	var polygonStyle;
	if(polygon!=null && styles.length>0){
		polygonStyle=VFG.Util.getEntityForPolygon(styles[0]);
	}
	var entity=VFG.Util.getEntityById(viewer,polygon.id);
	if(entity){
		VFG.Util.removeEntityById(viewer,polygon.id);
	}
	var points=[];
	if(polygon.points){
		points=JSON.parse(polygon.points);
		if(points.length>=2){
			var arrForC3=[];
			for(var i=0;i<points.length;i++){
				arrForC3.push(Cesium.Cartesian3.fromDegrees(points[i].x*1,points[i].y*1,points[i].z*1));
			}
			if(polygonStyle){
				polygonStyle.hierarchy=new Cesium.PolygonHierarchy(arrForC3)
				polygonStyle.clampToGround= true //开启贴地
			}
			
			VFG.Util.createPolygonPrimitive(viewer,{
				id:polygon.id,
				name:polygon.name||'',
				hierarchy:new Cesium.PolygonHierarchy(arrForC3)
			},polygonStyle);
		}

	}else{
		console.log('无效数据polygon');
	}
}

//线
VFG.Util.polyLineForCreate=function(viewer,polyLineRender){
	var _this=this;
	if(!polyLineRender){
		return;
	}
	var line=polyLineRender.line;
	var styles=polyLineRender.styles;
	if(!line){
		return;
	}
	var lineStyle;
	if(line!=null && styles.length>0){
		lineStyle=VFG.Util.getEntityForLine(styles[0]);
	}
	var entity=VFG.Util.getEntityById(viewer,line.id);
	if(entity){
		VFG.Util.removeEntityById(viewer,line.id);
	}
	if(line.points){
		var points=JSON.parse(line.points);
		var arrForC3=[];
		for(var i=0;i<points.length;i++){
			arrForC3.push(Cesium.Cartesian3.fromDegrees(points[i].x*1,points[i].y*1,points[i].z*1));
		}
		
		if(lineStyle){
			lineStyle.positions=arrForC3;
		}
		VFG.Util.createLinePrimitive(viewer,{
			id:line.id,
			name:line.name,
			code:line.code||'',
			positions:arrForC3
		},lineStyle);
	}else{
		console.log('无效数据line');
	}
}

/**
 * 获取多边形中心位置
 */
VFG.Util.getCenterForPolygon=function(viewer,positions, height) {
    try {
        if (positions.length == 1) {
            return positions[0];
        } else if (positions.length == 2) {
            return Cesium.Cartesian3.midpoint(positions[0], positions[1], new Cesium.Cartesian3());
        }
        
        var LnLas=[];
        var points=[];
        for(var i=0;i<positions.length;i++){
        	var lnla=this.getC3ToLnLa(viewer, positions[i]);
        	LnLas.push(lnla);
        	points.push([lnla.x,lnla.y]);
        }
        points.push(points[0]);
        var ds=[points]
        var polygon = turf.polygon(ds);
        var center = turf.centerOfMass(polygon);
        var coordinates=center.geometry.coordinates;
        var cartesian3=new Cesium.Cartesian3.fromDegrees(coordinates[0],coordinates[1],0);
    	var cartesian2=Cesium.SceneTransforms.wgs84ToWindowCoordinates(viewer.scene,cartesian3);
    	if (viewer.scene.mode !== Cesium.SceneMode.MORPHING) {
    		var pickedObject = viewer.scene.pick(cartesian2);
    		if (viewer.scene.pickPositionSupported && pickedObject) {
    			var carto=new Cesium.Cartographic.fromDegrees(coordinates[0],coordinates[1])
    			var sampleHeight = viewer.scene.sampleHeight(carto);
    			return new Cesium.Cartesian3.fromDegrees(coordinates[0],coordinates[1],sampleHeight);
    		}else{
    			var carto=new Cesium.Cartographic.fromDegrees(coordinates[0],coordinates[1])
        		var heightTerrain =  viewer.scene.globe.getHeight(carto);
    			return new Cesium.Cartesian3.fromDegrees(coordinates[0],coordinates[1],heightTerrain);
    		}
    	}else{
			var carto=new Cesium.Cartographic.fromDegrees(coordinates[0],coordinates[1])
    		var heightTerrain =  viewer.scene.globe.getHeight(carto);
			return new Cesium.Cartesian3.fromDegrees(coordinates[0],coordinates[1],heightTerrain);
    	}
    } catch (e) {
    	console.log(e);
        return positions[Math.floor(positions.length / 2)];
    }
}

/**

 * 获取坐标数组中最高高程值
 * @param {Array} positions Array<Cartesian3> 笛卡尔坐标数组
 * @param {Number} defaultVal 默认高程值

 */
VFG.Util.getMaxHeight=function(positions, defaultVal) {
    if (defaultVal == null) defaultVal = 0;
    var maxHeight = defaultVal;
    if (positions == null || positions.length == 0) return maxHeight;
    for (var i = 0; i < positions.length; i++) {
        var tempCarto = Cesium.Cartographic.fromCartesian(positions[i]);
        if (tempCarto.height > maxHeight) {
            maxHeight = tempCarto.height;
        }
    }
    return formatNum(maxHeight, 2);
}

//格式化 数字 小数位数
VFG.Util.formatNum=function(num, digits) {
    return Number(num.toFixed(digits || 0));
}

/**
 * 获取高度
 */
VFG.Util.getSurfaceHeight=function (viewer, position, opts) {
	var _this=this;
	var cartesian2=Cesium.SceneTransforms.wgs84ToWindowCoordinates(viewer.scene,position);
	if (viewer.scene.mode !== Cesium.SceneMode.MORPHING && cartesian2) {
		var pickedObject = viewer.scene.pick(cartesian2);
		if (viewer.scene.pickPositionSupported && Cesium.defined(pickedObject)) {
			return _this.getSurface3DTilesetHeight(viewer, position, opts);
		}
	}
	return _this.getSurfaceTerrainHeight(viewer, position, opts);
}

//
///**
//
// * 获取坐标的 贴模型高度
// * opts支持:   是否异步 asyn:true  异步回调方法calback返回“新高度”和“原始的Cartographic坐标”
// */
//VFG.Util.getSurface3DTilesHeight=function(scene, position, opts) {
//	var _this=this;
//    opts = opts || {};
//    //原始的Cartographic坐标
//    opts.cartesian = opts.cartesian || Cesium.Cartographic.fromCartesian(position);
//    var carto = opts.cartesian;
//
//    //是否异步求精确高度 
//    if (opts.asyn) {
//    	 var cartographic=Cesium.Cartographic.fromCartesian(position);
//        scene.sampleHeightMostDetailed([cartographic]).then(function (clampedPositions) {
//            var clampedPt = clampedPositions[0];
//            if (Cesium.defined(clampedPt)) {
//                var heightTiles = clampedPt.height;
//                if (Cesium.defined(heightTiles) && heightTiles > -1000) {
//                    if (opts.calback) opts.calback(heightTiles, clampedPt);
//                    return;
//                }
//            }else{
//            	_this.getSurfaceTerrainHeight(scene, position, opts);
//            }
//        });
//    } else {
//        //取贴模型高度
//        var heightTiles = scene.sampleHeight(carto);
//        if (Cesium.defined(heightTiles) && heightTiles > -1000) {
//            if (opts.calback) opts.calback(heightTiles, carto);
//            return heightTiles;
//        }
//    }
//    return 0; //表示取值失败
//}

/**
 * 获取坐标的 贴地高度
 * opts支持:   是否异步 asyn:true  异步回调方法calback
 */
//VFG.Util.getSurfaceTerrainHeight=function(scene, position, opts) {
//    opts = opts || {};
//    //原始的Cartographic坐标
//    var carto = opts.cartesian || Cesium.Cartographic.fromCartesian(position);
//    var _hasTerrain = VFG.Provider.hasTerrain; //是否有地形
//    if (!_hasTerrain) {
//        //不存在地形，直接返回
//        if (opts.calback) opts.calback(carto.height, carto);
//        return carto.height;
//    }
//
//    //是否异步求精确高度 
//    if (opts.asyn) {
//        Cesium.when(Cesium.sampleTerrainMostDetailed(scene.terrainProvider, [carto]), function (samples) {
//            var clampedCart = samples[0];
//            var heightTerrain;
//            if (Cesium.defined(clampedCart) && Cesium.defined(clampedCart.height)) {
//                heightTerrain = clampedCart.height;
//            } else {
//                heightTerrain = scene.globe.getHeight(carto);
//            }
//            if (opts.calback) opts.calback(heightTerrain, carto);
//        });
//    } else {
//        var heightTerrain = scene.globe.getHeight(carto);
//        if (Cesium.defined(heightTerrain) && heightTerrain > -1000) {
//            if (opts.calback) opts.calback(heightTerrain, carto);
//            return heightTerrain;
//        }
//    }
//    return 0; //表示取值失败
//}

/**
 * 获取模型表面高度
 * viewer:
 * cartesian3:笛卡尔坐标
 * opts:{
 * 	asyn:true/false
 * 	calback(e)：e模型表面高度
 * }
 */
VFG.Util.getSurfaceModelHeight=function(viewer, cartesian3, opts) {
	var cartographic=Cesium.Cartographic.fromCartesian(cartesian3);
	if (Cesium.defined(cartographic)){
		  var objectsToExclude = [cartographic];
		  var height;
		  if (viewer.scene.sampleHeightSupported) {
			  if (opts.asyn){
				  viewer.scene.sampleHeightMostDetailed(objectsToExclude).then(function(updatedPosition) {
					  height= positions[0].height;
					  if (Cesium.defined(height)){
						  if (opts.calback) {
							  opts.calback(height);
						  }
					  }else{
						  if (opts.calback) {
							  opts.calback(0);
						  } 
					  }
				  });
			  }else{
				  height = viewer.scene.sampleHeight(cartographic, objectsToExclude);
				  if (Cesium.defined(height)){
					  return height;
				  }
			  }
		  }
	}
	return 0;
}

/**
 * 获取3DTileset表面高度
 * cartesian3 笛卡尔坐标
 */
VFG.Util.getSurface3DTilesetHeight=function(viewer, cartesian3, opts) {
	var _this=this;
	if(Cesium.defined(cartesian3)){
		if (viewer.scene.clampToHeightSupported){
			if (opts && opts.asyn){
				viewer.scene.clampToHeightMostDetailed([cartesian3]).then(function(clampedCartesians) {
					var clampedPt = clampedCartesians[0];
		            if (Cesium.defined(clampedPt)) {
		                var heightTiles = Cesium.Cartographic.fromCartesian(clampedPt).height;
		                if (Cesium.defined(heightTiles) && heightTiles > -1000) {
		                	if (opts.calback) opts.calback(heightTiles);
		                }else{
		                	_this.getSurfaceTerrainHeight(viewer, cartesian3, opts);
		                }
		            }else{
		            	_this.getSurfaceTerrainHeight(viewer, cartesian3, opts);
		            }
				});
			}else{
				var c3=viewer.scene.clampToHeight(cartesian3);
				if (Cesium.defined(c3)){
					var LnLa=VFG.Util.getC3ToLnLa(viewer, c3);
					if(Cesium.defined(LnLa) &&  LnLa.z>-1000){
						return LnLa.z;
					}else{
					 _this.getSurfaceTerrainHeight(viewer, cartesian3, opts);
					}
				}
			}
		}else{
			_this.getSurfaceTerrainHeight(viewer, cartesian3, opts);
		}
	}
}

/**
 * 获取地表高度
 */
VFG.Util.getSurfaceTerrainHeight=function(viewer, cartesian3, opts) {
	if (Cesium.defined(viewer.scene.terrainProvider)){
		var cartographic=Cesium.Cartographic.fromCartesian(cartesian3);
		if (Cesium.defined(cartographic)){
			  var _hasTerrain = VFG.Provider.hasTerrain; //是否有地形
			  if (!_hasTerrain) {
			      if (opts.calback) opts.calback(cartographic.height);
			      return cartographic.height;
			  }
			  var objectsToExclude = [cartographic];
			  if (opts.asyn){
				  Cesium.sampleTerrainMostDetailed(viewer.scene.terrainProvider,objectsToExclude).then(function(samples) {
					    var heightTerrain;
			            var clampedCart = samples[0];
			            if (Cesium.defined(clampedCart) && Cesium.defined(clampedCart.height)) {
			                heightTerrain = clampedCart.height;
			    			if(heightTerrain<0){
			    				console.log(heightTerrain);
			    			}
			            } else {
			                heightTerrain = viewer.scene.globe.getHeight(cartographic);
			            }
			            if (opts.calback) opts.calback(heightTerrain);
				  })
			  }else{
			        var heightTerrain = viewer.scene.globe.getHeight(cartographic);
			        if (Cesium.defined(heightTerrain) && heightTerrain > -1000) {
			            return heightTerrain;
			        }
			  }
		}	
	}
	return 0;
}


VFG.Util.getCurrentExtent=function(viewer) {
    // 范围对象
    var extent = {};

    // 得到当前三维场景
    var scene = viewer.scene;

    // 得到当前三维场景的椭球体
    var ellipsoid = scene.globe.ellipsoid;
    var canvas = scene.canvas;

    // canvas左上角
    var car3_lt = viewer.camera.pickEllipsoid(new Cesium.Cartesian2(0, 0), ellipsoid);

    // canvas右下角
    var car3_rb = viewer.camera.pickEllipsoid(new Cesium.Cartesian2(canvas.width, canvas.height), ellipsoid);

    // 当canvas左上角和右下角全部在椭球体上
    if (car3_lt && car3_rb) {
        var carto_lt = ellipsoid.cartesianToCartographic(car3_lt);
        var carto_rb = ellipsoid.cartesianToCartographic(car3_rb);
        extent.xmin = Cesium.Math.toDegrees(carto_lt.longitude);
        extent.ymax = Cesium.Math.toDegrees(carto_lt.latitude);
        extent.xmax = Cesium.Math.toDegrees(carto_rb.longitude);
        extent.ymin = Cesium.Math.toDegrees(carto_rb.latitude);
    }

    // 当canvas左上角不在但右下角在椭球体上
    else if (!car3_lt && car3_rb) {
        var car3_lt2 = null;
        var yIndex = 0;
        do {
            // 这里每次10像素递加，一是10像素相差不大，二是为了提高程序运行效率
            yIndex <= canvas.height ? yIndex += 10 : canvas.height;
            car3_lt2 = viewer.camera.pickEllipsoid(new Cesium.Cartesian2(0, yIndex), ellipsoid);
        } while (!car3_lt2);
        var carto_lt2 = ellipsoid.cartesianToCartographic(car3_lt2);
        var carto_rb2 = ellipsoid.cartesianToCartographic(car3_rb);
        extent.xmin = Cesium.Math.toDegrees(carto_lt2.longitude);
        extent.ymax = Cesium.Math.toDegrees(carto_lt2.latitude);
        extent.xmax = Cesium.Math.toDegrees(carto_rb2.longitude);
        extent.ymin = Cesium.Math.toDegrees(carto_rb2.latitude);
    }

    // 获取高度
    extent.height = Math.ceil(viewer.camera.positionCartographic.height);
    return extent;
}

/**
 * viewer:viewer
 * cameraPosition:起点
 * position:目标
 */
VFG.Util.getHeadingPitchRoll = function (viewer,cameraPosition,position) {
	var _this=this;
    var e = cameraPosition,
    t = position,
    i = Cesium.Cartesian3.normalize(Cesium.Cartesian3.subtract(t, e, new Cesium.Cartesian3), new Cesium.Cartesian3),
    a = Cesium.Cartesian3.normalize(e, new Cesium.Cartesian3),
    n = new Cesium.Camera(viewer.scene);
    n.position = e,
    n.direction = i,
    n.up = a,
    i = n.directionWC,
    a = n.upWC;
    var r = n.rightWC,
    o = new Cesium.Cartesian3,
    l = new Cesium.Matrix3,
    u = new Cesium.Quaternion;
    r = Cesium.Cartesian3.negate(r, o);
    var d = l;
    Cesium.Matrix3.setColumn(d, 0, r, d),
    Cesium.Matrix3.setColumn(d, 1, a, d),
    Cesium.Matrix3.setColumn(d, 2, i, d);
    var c = Cesium.Quaternion.fromRotationMatrix(d, u);
    var hpr = Cesium.HeadingPitchRoll.fromQuaternion(c);
    
    //return hpr;
    // 得到角度
/*    var heading = Cesium.Math.toDegrees(hpr.heading);
    var pitch = Cesium.Math.toDegrees(hpr.pitch);
    var roll = Cesium.Math.toDegrees(hpr.roll);*/
    return hpr
};

/**
 * Turf多边形
 */
VFG.Util.getTurfPolygon = function (points) {
	var area=[];
	for(var i=0;i<points.length;i++){
		var point=[];
		point[0]=points[i].x;
		point[1]=points[i].y;
		area.push(point);
	}
	
	var point=[];
	point[0]=points[0].x;
	point[1]=points[0].y;
	area.push(point);
	return turf.polygon([area]);
}

/**
 * Turf点
 */
VFG.Util.getTurfPoint = function (point) {
	return turf.point([point.x*1, point.y*1]);
}

/**
 * 点是否在多边形内部
 */
VFG.Util.booleanPointInPolygon = function (polygon,point) {
	return turf.booleanPointInPolygon(point,polygon);
}


;
///<jscompress sourcefile="CesiumVFGWin.js" />
!function(e, t) {
	"object" == typeof exports && "object" == typeof module ? module.exports = t(require("Cesium"))
			: "function" == typeof define && define.amd ? define([ "Cesium" ],
					t)
					: "object" == typeof exports ? exports.CesiumVFGWin = t(require("Cesium"))
							: e.CesiumVFGWin = t(e.Cesium)
}("undefined" != typeof self ? self : this, function(cesium) {
	function _(viewer,option) {
		this.viewer = viewer;
		this.option = Cesium.defaultValue(option, Cesium.defaultValue.EMPTY_OBJECT);
		this.position=option.position;
		this.layerIndex=option.index;
		this.layero=option.layero;
		this.width;
		this.height;
		this.init();
	}
	_.prototype.init= function() {
		var _this=this;
		var cartesian2=Cesium.SceneTransforms.wgs84ToWindowCoordinates(_this.viewer.scene, _this.position);
		if (Cesium.defined(cartesian2)){
			_this.width=(layui.$(_this.layero).css('width').replace('px','')*1)/2;
			_this.height=(layui.$(_this.layero).css('height').replace('px','')*1)-15;
			layer.style(_this.layerIndex, {
				left:(cartesian2.x-_this.width)+'px',
				top:(cartesian2.y-_this.height)+'px'
			});
		}
    	_this.event=function(){
    		var cartesian2=Cesium.SceneTransforms.wgs84ToWindowCoordinates(_this.viewer.scene, _this.position);
    		if (Cesium.defined(cartesian2)){
        		layer.style(_this.layerIndex, {
    				left:(cartesian2.x-_this.width)+'px',
    				top:(cartesian2.y-_this.height)+'px'
        		});
    		}
    	}
    	_this.viewer.scene.postRender.addEventListener(_this.event);
	};
	_.prototype.destroy = function() {
		var _this = this;
		if(_this.event){
			_this.viewer.scene.postRender.removeEventListener(_this.event);
		}
		delete this.viewer,
		delete this.option,
		delete this.position,
		delete this.layerIndex;
		delete this.layero;
		delete this.width;
		delete this.height;
		return Cesium.destroyObject(this);
	};
	cesium.VFGWin= _;
});
///<jscompress sourcefile="VFG.js" />
function VFG() {
}

VFG.Globe=function(option){
	this.option = Cesium.defaultValue(option, Cesium.defaultValue.EMPTY_OBJECT);
	this.scene3DOnly=(option && option.scene3DOnly) ? option.scene3DOnly : true,
	this.selectionIndicator= (option && option.selectionIndicator) ? option.selectionIndicator :false,
	this.animation=(option && option.animation) ? option.animation : false,
	this.timeline= (option && option.timeline) ? option.timeline :false,
	this.navigationHelpButton=(option && option.navigationHelpButton) ? option.navigationHelpButton : false,
	this.fullscreenButton=(option && option.fullscreenButton) ? option.fullscreenButton : false,
	this.geocoder= (option && option.geocoder) ? option.geocoder :false,
	this.homeButton= (option && option.homeButton) ? option.homeButton :false,
	this.shouldAnimate= (option && option.shouldAnimate) ? option.shouldAnimate :false,
	this.sceneModePicker= (option && option.sceneModePicker) ? option.sceneModePicker :false,
	this.shouldAnimate= (option && option.shouldAnimate) ? option.shouldAnimate :true,
	this.infoBox= (option && option.infoBox) ? option.infoBox :false,
	this.requestRenderMode=(option && option.requestRenderMode) ? option.requestRenderMode : false,
	this.navigationInstructionsInitiallyVisible=(option && option.navigationInstructionsInitiallyVisible) ? option.navigationInstructionsInitiallyVisible :false,
	this.baseLayerPicker=(option && option.baseLayerPicker) ? option.baseLayerPicker :false,
	this.maximumRequests = (option && option.maximumRequests) ? option.maximumRequests :4096;
	this.maximumRequestsPerServer = (option && option.maximumRequestsPerServer) ? option.maximumRequestsPerServer :4096;
	this.throttleRequests = (option && option.throttleRequests) ? option.throttleRequests :true;
	this.defaultAccessToken = (option && option.defaultAccessToken) ? option.defaultAccessToken :'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJqdGkiOiJiZjliY2NhNS1iMThiLTQzZTYtOWM1ZS03NDMxMmY3YjIyNmUiLCJpZCI6MjAwNDcsInNjb3BlcyI6WyJhc2wiLCJhc3IiLCJhc3ciLCJnYyJdLCJpYXQiOjE1ODMxOTk3NTl9.lzdqsXU24bvovmmaRPXcD3jmSH0WmYTwmX6isCx8qfA';
	var _this = this;
	Cesium.RequestScheduler.maximumRequests = _this.maximumRequests;
	Cesium.RequestScheduler.maximumRequestsPerServer = _this.maximumRequestsPerServer;
	Cesium.RequestScheduler.throttleRequests = _this.throttleRequests;
	Cesium.Ion.defaultAccessToken = _this.defaultAccessToken;
	_this.viewer = new Cesium.Viewer(this.option.domId, {
		scene3DOnly: _this.scene3DOnly,
		selectionIndicator: _this.selectionIndicator,
		baseLayerPicker: _this.baseLayerPicker,
		animation: _this.animation,
		timeline: _this.timeline,
		navigationHelpButton: _this.navigationHelpButton,
		fullscreenButton: _this.fullscreenButton,
		geocoder: _this.geocoder,
		homeButton: _this.homeButton,
		shouldAnimate: _this.shouldAnimate,
		sceneModePicker: _this.sceneModePicker,
		shouldAnimate: _this.shouldAnimate,
		infoBox: _this.infoBox,
		requestRenderMode: _this.requestRenderMode,
		navigationInstructionsInitiallyVisible: _this.navigationInstructionsInitiallyVisible,
		baseLayerPicker: _this.baseLayerPicker,
		contextOptions: {
		webgl: {
			  alpha: true,
			  depth: true,
			  stencil: true,
			  antialias: true,
			  premultipliedAlpha: true,
			  preserveDrawingBuffer:true,
			  failIfMajorPerformanceCaveat:true
			}
		},
		imageryProvider: (_this.option && _this.option.imageryProvider) ?_this.option.imageryProvider: null
	});
	this.viewer.scene.globe.depthTestAgainstTerrain = false;
	this.viewer.cesiumWidget.creditContainer.style.display = "none";
	
    //设置操作习惯(禁止中间滑轮调整视角)
	this.viewer.scene.screenSpaceCameraController.zoomEventTypes = [Cesium.CameraEventType.WHEEL, Cesium.CameraEventType.PINCH];
	this.viewer.scene.screenSpaceCameraController.tiltEventTypes = [Cesium.CameraEventType.PINCH, Cesium.CameraEventType.RIGHT_DRAG];
	
	//解决模糊问题
	if(Cesium.FeatureDetection.supportsImageRenderingPixelated()){//判断是否支持图像渲染像素化处理
		this.viewer.resolutionScale = window.devicePixelRatio;
	}
	//是否开启抗锯齿
	this.viewer.scene.fxaa = true;
	this.viewer.scene.postProcessStages.fxaa.enabled = true;
	
	// 去掉entity的点击事件 start
	this.viewer.cesiumWidget.screenSpaceEventHandler.removeInputAction(Cesium.ScreenSpaceEventType.LEFT_DOUBLE_CLICK);
	this.viewer.cesiumWidget.screenSpaceEventHandler.removeInputAction(Cesium.ScreenSpaceEventType.LEFT_CLICK)
	this.viewer.scene.globe.baseColor = new Cesium.Color.fromCssColorString("#546a53"); //地表背景色
	
    //限制缩放级别
	this.viewer.scene.screenSpaceCameraController.maximumZoomDistance =20000000; //变焦时相机位置的最大值（以米为单位） 
	this.viewer.scene.screenSpaceCameraController.minimumZoomDistance =1; //变焦时相机位置的最小量级（以米为单位）。默认为1.0。

	this.viewer.scene.screenSpaceCameraController._zoomFactor = 3; //鼠标滚轮放大的步长参数 
	this.viewer.scene.screenSpaceCameraController.minimumCollisionTerrainHeight = 15000000; //低于此高度时绕鼠标键绕圈，大于时绕视图中心点绕圈。
	
	// 亮度设置
	
	var _this=this;
	this.viewer.dataSources.add(VFG.Point.Layers);
	this.viewer.dataSources.add(VFG.Polyline.Layers);
	this.viewer.dataSources.add(VFG.Polygon.Layers);//面实体图层
	
	this.viewer.scene.primitives.add(VFG.Model.Layers);//模型图层
	this.viewer.scene.primitives.add(VFG.Model.Feature.Layers);//单体图层
	this.viewer.scene.primitives.add(VFG.Point.LabelCollection);
	this.viewer.scene.primitives.add(VFG.Point.PointPrimitiveCollection);
	this.viewer.scene.primitives.add(VFG.Point.BillboardCollection);
	
	/*this.viewer.dataSources.add(VFG.Point.Layers).then(function (dataSource) {
		   var pixelRange = 15;
		    var minimumClusterSize = 3;
		    var enabled = true;
		    dataSource.clustering.enabled = enabled;
		    dataSource.clustering.pixelRange = pixelRange;
		    dataSource.clustering.minimumClusterSize = minimumClusterSize;
		    var removeListener;
		    function customStyle() {
		        if (Cesium.defined(removeListener)) {
		            removeListener();
		            removeListener = undefined;
		        } else {
		            removeListener = dataSource.clustering.clusterEvent.addEventListener(function(clusteredEntities, cluster) {
		                cluster.label.show = false;
		                cluster.billboard.show = true;
		                cluster.billboard.id = cluster.label.id;
		                if (clusteredEntities.length >= 50) {
		                    cluster.billboard.image = _this.getIconForRed(clusteredEntities.length,55,55);
		                } else if (clusteredEntities.length >= 40) {
		                    cluster.billboard.image = _this.getIconForYellow(clusteredEntities.length,50,50);
		                } else if (clusteredEntities.length >= 30) {
		                    cluster.billboard.image = _this.getIconForOrange(clusteredEntities.length,45,45);
		                } else if (clusteredEntities.length >= 20) {
		                    cluster.billboard.image = _this.getIconForPurple(clusteredEntities.length,40,40);
		                } else if (clusteredEntities.length >= 10) {
		                    cluster.billboard.image = _this.getIconForBlue(clusteredEntities.length,35,35);
		                } else {
		                    cluster.billboard.image = _this.getIconForGreen(clusteredEntities.length,30,30);
		                }
		            });
		        }
		        var pixelRange = dataSource.clustering.pixelRange;
		        dataSource.clustering.pixelRange = 0;
		        dataSource.clustering.pixelRange = pixelRange;
		    }
		  	customStyle();
	  });*/
	this.viewer.scene.debugShowFramesPerSecond = true;
}

VFG.Globe.prototype.getIconForRed=function(number,width,height) {
    var canvas=document.createElement('canvas');
    canvas.width=width||48;
    canvas.height=height||48;
    var ctx=canvas.getContext("2d");
    ctx.beginPath();
    ctx.fillStyle = 'rgba(255,0,0,0.5)'; // 红	
    ctx.arc(canvas.width/2,canvas.height/2,canvas.width/2,0,2*Math.PI, false);
    ctx.fill();
    ctx.beginPath();	
    ctx.fillStyle = 'rgba(255, 0,0,1)'; // 红	
    ctx.arc(canvas.width/2,canvas.height/2,canvas.width/2-5,0,2*Math.PI,false);
    ctx.fill();	
    ctx.fillStyle="rgb(255,255,255)";
    ctx.textAlign = "center";
    ctx.textBaseline = "middle";
    ctx.font="16px bold sans-serif";
    ctx.fillText(number,canvas.width/2,canvas.height/2+2);
    return  canvas.toDataURL("image/png")
}
VFG.Globe.prototype.getIconForYellow=function(number,width,height) {
    var canvas=document.createElement('canvas');
    canvas.width=width||48;
    canvas.height=height||48;
    var ctx=canvas.getContext("2d");
    ctx.beginPath();
    ctx.fillStyle = 'rgba(255,255,0,0.5)'; // 红	
    ctx.arc(canvas.width/2,canvas.height/2,canvas.width/2,0,2*Math.PI, false);
    ctx.fill();
    ctx.beginPath();	
    ctx.fillStyle = 'rgba(255,255,0,1)'; // 红	
    ctx.arc(canvas.width/2,canvas.height/2,canvas.width/2-5,0,2*Math.PI,false);
    ctx.fill();	
    ctx.fillStyle="rgb(255,255,255)";
    ctx.textAlign = "center";
    ctx.textBaseline = "middle";
    ctx.font="16px bold sans-serif";
    ctx.fillText(number,canvas.width/2,canvas.height/2+2);
    return  canvas.toDataURL("image/png")
}
VFG.Globe.prototype.getIconForOrange=function(number,width,height) {
    var canvas=document.createElement('canvas');
    canvas.width=width||48;
    canvas.height=height||48;
    var ctx=canvas.getContext("2d");
    ctx.beginPath();
    ctx.fillStyle = 'rgba(255,165,0,0.5)'; // 红	
    ctx.arc(canvas.width/2,canvas.height/2,canvas.width/2,0,2*Math.PI, false);
    ctx.fill();
    ctx.beginPath();	
    ctx.fillStyle = 'rgba(255,165,0,1)'; // 红	
    ctx.arc(canvas.width/2,canvas.height/2,canvas.width/2-5,0,2*Math.PI,false);
    ctx.fill();	
    ctx.fillStyle="rgb(255,255,255)";
    ctx.textAlign = "center";
    ctx.textBaseline = "middle";
    ctx.font="16px bold sans-serif";
    ctx.fillText(number,canvas.width/2,canvas.height/2+2);
    return  canvas.toDataURL("image/png")
}

VFG.Globe.prototype.getIconForPurple=function(number,width,height) {
    var canvas=document.createElement('canvas');
    canvas.width=width||48;
    canvas.height=height||48;
    var ctx=canvas.getContext("2d");
    ctx.beginPath();
    ctx.fillStyle = 'rgba(160,32,240,0.5)'; // 红	
    ctx.arc(canvas.width/2,canvas.height/2,canvas.width/2,0,2*Math.PI, false);
    ctx.fill();
    ctx.beginPath();	
    ctx.fillStyle = 'rgba(160,32,240,1)'; // 红	
    ctx.arc(canvas.width/2,canvas.height/2,canvas.width/2-5,0,2*Math.PI,false);
    ctx.fill();	
    ctx.fillStyle="rgb(255,255,255)";
    ctx.textAlign = "center";
    ctx.textBaseline = "middle";
    ctx.font="16px bold sans-serif";
    ctx.fillText(number,canvas.width/2,canvas.height/2+2);
    return  canvas.toDataURL("image/png")
}
VFG.Globe.prototype.getIconForBlue=function(number,width,height) {
    var canvas=document.createElement('canvas');
    canvas.width=width||48;
    canvas.height=height||48;
    var ctx=canvas.getContext("2d");
    ctx.beginPath();
    ctx.fillStyle = 'rgba(0,0,255,0.5)'; // 红	
    ctx.arc(canvas.width/2,canvas.height/2,canvas.width/2,0,2*Math.PI, false);
    ctx.fill();
    ctx.beginPath();	
    ctx.fillStyle = 'rgba(0,0,255,1)'; // 红	
    ctx.arc(canvas.width/2,canvas.height/2,canvas.width/2-5,0,2*Math.PI,false);
    ctx.fill();	
    ctx.fillStyle="rgb(255,255,255)";
    ctx.textAlign = "center";
    ctx.textBaseline = "middle";
    ctx.font="16px bold sans-serif";
    ctx.fillText(number,canvas.width/2,canvas.height/2+2);
    return  canvas.toDataURL("image/png")
}

VFG.Globe.prototype.getIconForGreen=function(number,width,height) {
    var canvas=document.createElement('canvas');
    canvas.width=width||48;
    canvas.height=height||48;
    var ctx=canvas.getContext("2d");
    ctx.beginPath();
    ctx.fillStyle = 'rgba(0,255,0,0.5)'; // 红	
    ctx.arc(canvas.width/2,canvas.height/2,canvas.width/2,0,2*Math.PI, false);
    ctx.fill();
    ctx.beginPath();	
    ctx.fillStyle = 'rgba(0,255,0,1)'; // 红	
    ctx.arc(canvas.width/2,canvas.height/2,canvas.width/2-5,0,2*Math.PI,false);
    ctx.fill();	
    ctx.fillStyle="rgb(255,255,255)";
    ctx.textAlign = "center";
    ctx.textBaseline = "middle";
    ctx.font="16px bold sans-serif";
    ctx.fillText(number,canvas.width/2,canvas.height/2+2);
    return  canvas.toDataURL("image/png")
}
;
///<jscompress sourcefile="ModelFeature.js" />
/**
 * 坐标点操作
 */
VFG.Model.Feature=function(){
}
VFG.Model.Feature.Layers= new Cesium.PrimitiveCollection();
VFG.Model.Feature.Map= new Map();

/**
 * id查询点
 */
VFG.Model.Feature.getFeatureById=function(id){
	if(this.Map.has(id)){
		return this.Map.get(id);
	}
}

/**
 * 删除单体
 */
VFG.Model.Feature.removeFeatureById=function(id){
	if(this.Map.has(id)){
		var primitive =this.Map.get(id);
		if(this.Layers.remove(primitive)){
			this.Map.delete(id);
			return true;
		}
	}
}

/**
 * 单体
 * params{
 *   id:主键
 *   name：名称
 *   code：标识
 *   position：经纬度
 *   rotation:旋转角
 *   dimensions：长宽高
 *   normalColor：模型原色
 *   hoverColor:鼠标悬浮颜色
 * }
 * 
 */
VFG.Model.Feature.addFeature=function(params){
	if(params && params.id){
		var primitive=this.getFeatureById(params.id);
		if(primitive){
			return primitive;
		}
	}
	var classification =new VFG.ClassificationPrimitive(params);
	if(classification && classification.primitive){
		this.Layers.add(classification.primitive);
		this.Map.set(classification.id,classification);
	}
	return classification;
}

/**
 * 平移
 */
VFG.Model.Feature.translateFeature=function(id,position){
	var modelFeature=this.getFeatureById(id);
	if(!modelFeature){
		return;
	}
    modelFeature.translateFeature(position);
}

/**
 * 更新尺寸
 */
VFG.Model.Feature.setDimensions=function(id,dimensions){
	var modelFeature=this.getFeatureById(id);
	if(!modelFeature){
		return;
	}
	this.Layers.remove(modelFeature.primitive)
	modelFeature.setDimensions(dimensions);
	if(modelFeature && modelFeature.primitive){
		this.Layers.add(modelFeature.primitive);
	}
}

/**
 * 设置颜色
 */
VFG.Model.Feature.setNormalColor=function(id,color){
	var modelFeature=this.getFeatureById(id);
	if(!modelFeature){
		return;
	}
    modelFeature.setNormalColor(color) ;
}

/**
 * 设置悬浮颜色
 */
VFG.Model.Feature.setHoverColor=function(id,color){
	var modelFeature=this.getFeatureById(id);
	if(!modelFeature){
		return;
	}
    modelFeature.setHoverColor(color) ;
}

/**
 * 是否长显示
 */
VFG.Model.Feature.setDisplay=function(id,isView){
	var modelFeature=this.getFeatureById(id);
	if(!modelFeature){
		return;
	}
    modelFeature.setDisplay(isView);
}

/**
 * 旋转
 */
VFG.Model.Feature.rotateFeature=function(id,rotation){
	var modelFeature=this.getFeatureById(id);
	if(!modelFeature){
		return;
	}
	modelFeature.rotateFeature(rotation);
}





/**
 * 接口添加点
 */
VFG.Model.Feature.addFeatureFromAPI=function(feature){
	var _this=this;
	return _this.addFeature({
		id:feature.id,
		name:feature.name,
		position:{
			x:feature.positionX,
			y:feature.positionY,
			z:feature.positionZ,
		},
		dimensions:{
			x:feature.dimensionsX,
			y:feature.dimensionsY,
			z:feature.dimensionsZ,
		},
		rotation:{
			x:feature.rotationX,
			y:feature.rotationY,
			z:feature.rotationZ,
		},
		normalColor:feature.normalColor,
		hoverColor:feature.hoverColor,
		code:feature.code,
		isView:feature.isView,
		type:'Feature',
	});	
}

/**
 * 批量添加接口点
 */
VFG.Model.Feature.batchAddFeatureFromAPI=function(viewer,Features){
	var _this=this;
    if(Features!=null && Features.length>0){
    	for(var i=0;i<Features.length;i++){
    		_this.addFeatureFromAPI(Features[i]);
    	}
    }
/*    var canvasPrimitive=new VFG.CanvasPrimitive(viewer,{
		id:VFG.Util.getUuid(),
		text:"收到回复决定是否接受大家",
		position:{
			x:102.84975959112421,
			y:24.842498345326277,
			z:1941,
		},
		rotation:{
			x:0,
			y:0,
			z:0,
		},
		type:'Canvas',    	
    });*/
   // this.Layers.add(canvasPrimitive.primitive);
}



;
